06. Object Iteration
Last updated
Was this helpful?
Last updated
Was this helpful?
Перечисляемые свойства --- это те свойства, для которых внутренний атрибут ключа выставлен в enumerable = true
. Перечисляемые свойства можно перебрать в цикле for..in
, за исключением полей-символов.
Принадлежность свойства определяется тем, принадлежит ли свойство самому объекту, или находится в его цепочке прототипов.
Собственные свойства принадлежат самому объекту, а
Унаследованные свойства принадлежат его прототипу.
В ES6 порядок перебора ключей стандартизирован:
Все индексы массивов, отсортированные по возрастанию. Индекс массива - специальный ключ-строка, хранящий число 0..2^32−1
.
Все строковые ключи, в том порядке, в котором они объявлены.
Все символы, в том порядке в котором они объявлены.
В зависимости от способа перечисления можно получить разные свойства:
for-in
Цикл for..in
перебирает перечисляемые свойства объекта в произвольном порядке, включая унаследованные:
Особенности:
Порядок не определен
Перечисляются так же и наследуемые свойства по всей цепочке прототипов.
Если необходимо перечислять только собственные свойства объекта, их необходимо фильтровать
Если свойство объекта отмечено как enumerable: false
, то оно не будет встречаться в цикле.
В теле цикла можно изменять объект, а так же удалять его свойства.
hasOwnProperty
guardCommon pattern consisting of for..in
with Object.prototype.hasOwnProperty
guards:
Note that in this particular case, the Object#hasOwnProperty
guard is not used properly, because the lookup happens on the obj
itself, which leads to potential performance issues, i.e. if you pass many different shapes of objects then the obj.hasOwnProperty
access will become megamorphic, but might also turn into a correctness issue, i.e. if obj
has a null
prototype because obj
was created via Object.create(null)
, then the expression obj.hasOwnProperty
will raise an error. So make sure to always follow the advice to write Object.prototype.hasOwnProperty.call(obj, prop)
instead, which is safe and avoids the potential negative performance impact:
for-of
Конструкция for..of
в начале своего выполнения автоматически вызывает Symbol.iterator()
, получает итератор и далее вызывает метод next()
до получения done: true
. Если функционал по перебору (метод next
) предоставляется самим объектом, то можно вернуть this
в качестве итератора:
Создание собственного итератора:
Object.keys()
, Object.values()
Object.keys() : Array<string>
--- возвращает массив имен собственных перечислимых свойств объекта.
Не возвращает унаследованные свойства
Похожие функции, работающие по тем же принципам:
Object.values
Object.entries
Object.getOwnPropertyNames()
Object.getOwnPropertyNames() : Array<string>
- действует подобно функции Object.keys()
, но возвращает имена всех собственных свойств указанного объекта, а не только перечислимые. Порядок свойств такой же, как при ручном переборе объекта в цикле.
Похожие методы:
Object.getOwnPropertySymbols(obj) : Array<symbol>
-- возвращает все собственные ключи-символы объекта.
Reflect.ownKeys(obj) : Array<string|symbol>
--- возвращает все ключи всех свойств объекта.
Reflect.enumerate(obj) : Iterator
- возвращает все строковые значения всех перечисляемых свойств.