переименовать hasOwnProperty, но запретить перечисление

#javascript #enumeration #prototype-programming

#javascript #перечисление #прототип-программирование

Вопрос:

Мне приходится часто использовать hasOwnProperty в моем коде, и это раздражающе долго и неудобно для ввода. Я хотел иметь возможность просто сказать myObj.has('x') , но когда я попытался создать псевдоним для перехода в Object.prototype ‘has’ теперь перечисляется в for..in циклы. Каков наилучший способ получить то, что я хочу? Я имею в виду, что я мог бы просто создать глобальную функцию, которая работает как has(obj, prop) но мне больше нравится формат dot, и я хотел бы знать, какие хитрости могут быть у javascript в рукаве, поэтому я ищу предложения.

Обновление: это кажется довольно сложным, но String.prototype.in = function(obj){return obj.hasOwnProperty(this)} все в порядке? После этого я могу сказать, if ( 'x'.in(myObj) ) {... к сожалению, это добавляет еще один уровень вызова функции, а не просто псевдоним hasOwnProperty, но мне нравится синтаксис.

Ответ №1:

Вы можете запретить перечисление только в браузерах, совместимых с ES5, используя Object.defineProperty() :

 Object.defineProperty(myObj, "has", { value: Object.prototype.hasOwnProperty });
  

defineProperty() по умолчанию задаются свойства, не подлежащие перечислению. Лучшим подходом ES3 было бы просто присвоить функции псевдоним и не подключать ее Object.prototype :

 var has = function (ob, prop) { 
    return Object.prototype.hasOwnProperty.call(ob, prop); 
}
  

Я также не вижу ничего плохого в вашем собственном String.prototype.in подходе, за исключением, возможно, потенциальных конфликтов именования в будущем, но это ваше дело. Его вызов String.prototype.on устранил бы двусмысленность с in оператором.

Комментарии:

1. Спасибо. Я пытался использовать defineProperty раньше, но, думаю, я использовал его неправильно

Ответ №2:

Это должно сработать

 Object.prototype.has = function(x) {
  return this.hasOwnProperty(x)
}
  

Будьте осторожны при использовании SomeNativeThing.prototype и используйте

 if ((typeof Object.prototype.has) !== 'function') {
   ...
}
  

чтобы убедиться, что вы ничего не переопределяете

как утверждает @pomeh, использование Object.prototype.has = Object.prototype.hasOwnProperty намного лучше

Комментарии:

1. почему бы и нет Object.prototype.has = Object.prototype.hasOwnProperty; ?

2. примечание: не расширяйте Object.prototype. вместо этого расширить MyObject.prototype

3. Э-э, вы игнорируете важную половину моего вопроса «… но предотвратите перечисление». Я уже пробовал способ помеха, но затем я получаю ошибки в моем for..in циклы, потому что «has» отображается для каждого базового объекта как перечислимый.