Количество элементов в объекте javascript

Есть ли способ получить (откуда-нибудь) количество элементов в объекте javascript ?? (то есть постоянная сложность).

Я не могу найти свойство или метод, позволяющий получить эту информацию. Пока я могу думать только об итерации по всей коллекции, но это линейное время.
Странно, что нет прямого доступа к размеру объекта, вам не кажется.

РЕДАКТИРОВАТЬ:
Я говорю об объекте Object (а не об объектах в целом):

var obj = new Object ;

person GetFree    schedule 05.06.2009    source источник
comment
Уже ответил здесь stackoverflow.com/questions/126100/ Object.keys (obj) .length   -  person spats    schedule 14.06.2012


Ответы (5)


Хотя реализации JS могут отслеживать такое значение внутренне, стандартного способа получить его не существует.

В прошлом вариант Javascript Mozilla предоставлял нестандартный __count__ , но он был удален в версии 1.8.5.

Для кроссбраузерного скриптинга вы застряли в явном переборе свойств и проверке hasOwnProperty():

function countProperties(obj) {
    var count = 0;

    for(var prop in obj) {
        if(obj.hasOwnProperty(prop))
            ++count;
    }

    return count;
}

В случае реализаций, поддерживающих ECMAScript 5, это также можно записать как (Престижность Avi Flax)

function countProperties(obj) {
    return Object.keys(obj).length;
}

Имейте в виду, что вы также пропустите свойства, которые нельзя перечислить (например, length массива).

Если вы используете фреймворк, например jQuery, Prototype, Mootools, $ what-the-newest-hype, проверьте, поставляются ли они со своим собственным API коллекций, что может быть лучшим решением вашей проблемы, чем использование собственных объектов JS.

person Christoph    schedule 05.06.2009
comment
Черт возьми, я всегда забываю hasOwnProperty. Слишком много времени на земле .NET, говорю вам. +1 - person annakata; 05.06.2009
comment
jQuery использует объект для своих коллекций, который он получает из запросов, и предоставляет это значение с помощью свойства length. - person Nosredna; 05.06.2009
comment
Firefox4 __count__ ушел :( - person Timo Huovinen; 11.04.2011
comment
Есть ли способ сделать это без for in? Я использую тот же тип привязки, но я бы хотел, чтобы он передавал JSLint, если это вообще возможно. - person streetlight; 30.01.2013
comment
зачем нам hasOwnProperty()? - person swisswiss; 20.02.2020

Для этого в любой ES5-совместимой среде

Object.keys(obj).length

(Поддержка браузера здесь)
(Документ по Object.keys здесь, включает метод, который вы можете добавить в браузеры, отличные от ECMA5)

person ZelkiN    schedule 15.03.2013
comment
Это неправильный вопрос, чтобы давать такой ответ. При этом вы берете все ключи объекта, помещаете их во вновь созданный массив, а затем извлекаете свойство length из этого нового массива. - person GetFree; 30.03.2013
comment
Возможно, он не самый эффективный с точки зрения программирования, но он наиболее эффективен для разработчиков. - person superluminary; 27.03.2016
comment
Я согласен, это определенно самый быстрый (короткий, быстро сделанный) способ сделать это. Также хорошо работает с вложенными объектами, если вас интересуют только собственные ключи подобъекта, Object.keys(obj.nested_obj).length. - person andiOak; 02.10.2020

Если вы уже используете jQuery в своей сборке, просто сделайте следующее:

$(yourObject).length

У меня это хорошо работает с объектами, и у меня уже был jQuery в качестве зависимости.

person IndelibleHeff    schedule 02.12.2014
comment
Странно ... у меня это не работает. Я всегда получаю 1. Ответ ZelkiN у меня работает. - person mike rodent; 13.06.2017
comment
Этот код всегда возвращает 1. Всего 1 объект. Это не считая элементов в нем - person BeRocket; 28.05.2018

AFAIK, нет возможности сделать это надежно, если вы не переключитесь на массив. Что, честно говоря, не кажется странным - мне кажется довольно очевидным, что массивы являются счетными, а объекты - нет.

Вероятно, самое близкое, что вы получите, это что-то вроде этого

// Monkey patching on purpose to make a point
Object.prototype.length = function()
{
  var i = 0;
  for ( var p in this ) i++;
  return i;
}

alert( {foo:"bar", bar: "baz"}.length() ); // alerts 3

Но это создает проблемы или, по крайней мере, вопросы. Учитываются все свойства, созданные пользователем, включая саму функцию _length! И хотя в этом простом примере вы можете избежать этого, просто используя обычную функцию, это не значит, что вы можете запретить другим скриптам делать это. так что ты делаешь? Игнорировать свойства функции?

Object.prototype.length = function()
{
  var i = 0;
  for ( var p in this )
  {
      if ( 'function' == typeof this[p] ) continue;
      i++;
  }
  return i;
}

alert( {foo:"bar", bar: "baz"}.length() ); // alerts 2

В конце концов, я думаю, вам, вероятно, следует отказаться от идеи делать свои объекты счетными и найти другой способ делать то, что вы делаете.

person Peter Bailey    schedule 05.06.2009
comment
ОПАСНО БУДЕТ РОБИНСОН! НЕ прото против Object! Все происходит от Object, вы нарушите клиентскую обработку таким образом, если выполняете какой-либо значительный объем JS-работы. - person annakata; 05.06.2009
comment
Эээ ... разве вы не читали ту часть, где я написал в комментарии к Monkey patching специально, чтобы подчеркнуть - да ладно, я сделал это намеренно, чтобы люди немного не волновались по этому поводу. Кроме того, даже если я не сторонник обезьяньего патча, вы неправильно понимаете, как работает цепочка прототипов в Javascript, если думаете, что это вызовет проблемы с производительностью video.yahoo.com/watch/111585/1027823 - person Peter Bailey; 05.06.2009
comment
Итак .. это делать или не делать? - person OscarRyz; 02.03.2012
comment
В Javascript: The Good Parts он создает прототип объекта с помощью метода create (). Я полагаю, что это окончательная книга по Javascript. - person Chris Dutrow; 13.03.2012

Концепция числа / длины / размерности на самом деле не имеет смысла для объекта, и необходимость в этом предполагает, что вы действительно хотите для меня массив.

Изменить: указал мне, что вам нужен O (1) для этого. Боюсь, что, насколько мне известно, такого способа не существует.

person annakata    schedule 05.06.2009
comment
Он предложил повторить сам, каково это решение. Ему нужен был способ O (1) для достижения этой цели ... - person Thomas Hansen; 05.06.2009
comment
Вы совершенно правы. Действительно стоит более внимательно читать вопросы. - person annakata; 05.06.2009
comment
Собственно, объекты - это самое близкое к Map, что есть в JS. Карты действительно имеют длину. - person Cristian Vrabie; 14.06.2012