Являются ли конечные запятые в массивах и объектах частью спецификации?

215

Являются ли конечные запятые стандартными в JavaScript, или большинство браузеров, таких как Chrome и Firefox, просто допускают их?

Я думал, что они были стандартными, но IE8 вырвался после столкновения с ним - конечно, IE, не поддерживающий что-то, вряд ли означает, что это не стандарт.

Вот пример того, что я имею в виду (после последнего элемента массива books):

var viewModel = {
    books: ko.observableArray([
        { title: "..", display: function() { return ".."; } },
        { title: "..", display: function() { return ".."; } },
        { title: "..", display: function() { return ".."; } }, // <--right there
    ]),
    currentTemplate: ko.observable("bookTemplate1"),
    displayTemplate: function() { return viewModel.currentTemplate(); }
};
Адам Рэкис
источник
Нашел это на днях. Будучи программистом на C #, я так привык к тому, что им позволили ...
CaffGeek
5
Я имел дело с этим несколько недель назад. Представьте, что вы пытаетесь найти это в IE7 без каких-либо новых средств отладки ...
Райан Миллер
4
Меня порадовало, когда я обнаружил, что такие языки, как JS, Ruby, C #, поддерживают это - делает тестовые вставки данных копирования легкими ... меня разозлило, когда я понял, что IE
впитывает
Интересно, может ли значительный пробел вместо запятых (вроде CoffeeScript) вызвать какую-либо синтаксическую неоднозначность?
Энди

Ответы:

209

Спецификации: ECMAScript 5 и ECMAScript 3


Раздел 11.1.5 в спецификации ECMAScript 5:

ObjectLiteral :
    { }
    { PropertyNameAndValueList }
    { PropertyNameAndValueList , }

Так что да, это часть спецификации.

Обновление: видимо, это новое в ES5. В ES3 (стр. 41) определение было просто:

ObjectLiteral :
    { }
    { PropertyNameAndValueList }

Для литералов массивов ( раздел 11.1.4 ) это еще более интересно ( обновление: это уже существовало в ES3):

ArrayLiteral :
    [ Elisionopt ]
    [ ElementList ]
    [ ElementList , Elision_opt ]

(где Elision_optElision opt , что означает, что Elision является необязательным)

Elision определяется как

Elision :
    ,
    Elision ,

Таким образом, массив буквального типа

var arr = [1,2,,,,];

совершенно законно. Это создает массив с двумя элементами, но устанавливает длину массива в2 + 3 = 5 .

Не ожидайте слишком многого от IE (до IE9) ...

Феликс Клинг
источник
1
Как я спросил EndoPhage, вы случайно не знаете, было ли это стандартом и в ES3? Я не могу найти спецификацию для этого
Адам Рэкис
2
Это здесь: ecma-international.org/publications/files/ECMA-ST-ARCH/…
Феликс Клинг
1
По-видимому, запятая в литералах объекта не была в спецификации ES3. Но определение для массивов то же самое.
Феликс Клинг
Ну, это были элементы массива, с которыми я столкнулся, так что я думаю, нет никакого оправдания для MS, как бы вы ее ни вырезали.
Еще
Позор на Micro $ oft Internet Explorer
обозревателю
91

Просто быстрое напоминание / предупреждение, что это одна из областей, в которой стандарт JavaScript / ECMAScript и стандарт JSON отличаются; конечные запятые действительны в JS, но недопустимы в JSON.

Джои Сабей
источник
1
Но с другой стороны, если надмножество готовится к «Изменению Сердца», «Можете ли вы (все еще) быть любимым», если вы хотя бы раз настроитесь?
Лукас Бюнгер
52

Что еще смешнее, IE7 дает

[1,].length  --> 2

пока Firefox и Chrome

[1,].length  --> 1
Seeg
источник
16
Но [1,,].lengthдает 2. Смысл : браузеры не делают ни одного.
Дэвид Титаренко
84
Имеет смысл, спецификация говорит, что конечная запятая (примечание: единственное) не увеличивает длину массива. Chrome и Firefox правильно реализовали ES5.
JaredMcAteer
7
Когда имеется 2 (множественные) конечные запятые, к длине массива добавляется только одна, поэтому точнее сказать, что последняя запятая игнорируется, чем пропустить одну запятую.
иконоборчество
4

Вы можете найти спецификацию для javascript (он же ECMA Script) здесь . Соответствующее определение для массивов вы можете найти на странице 63, и, как заметил Феликс, определение объекта пару страниц позже на странице 65.

Хотя эта спецификация говорит, что хорошо иметь трейлинг, ,я не знаю, будет ли это правдой, оглядываясь назад на несколько версий. Как вы уже заметили, IE8 будет самодовольным, если оставить запятую, но Chrome и FF справятся с этим.

Endophage
источник
Вне головы, была ли это часть стандарта ES3? Я не могу найти спецификацию ES3
Адам Рэкис
1
@ Adam Я пытался найти его ... Учитывая даты выпуска (ES3 была опубликована в 1999 году, ES4 была отменена, а ES5 была опубликована только в 2009 году), было бы разумно, чтобы она была в стандарте ES3. Или может быть, что MS облажалась еще одна вещь.
Эндофаг
Похоже, М.С. испортил еще одну вещь, учитывая ответ Феликса.
Еще
2

Давайте разберемся с этим.

Являются ли конечные запятые стандартными в JavaScript?

Да. Начиная со спецификации ECMAScript 5 (также является частью руководства по стилям Google и Airbnb)

Большинство браузеров, таких как Chrome и Firefox, просто терпят их?

Это вопрос поддержки ECMAScript 5.

Транспортеры, такие как Babel, удалят дополнительную запятую в переносимом коде, что означает, что вам не нужно беспокоиться о проблеме запятой в устаревших браузерах.

Так что это означает:

var heroes = [
  'Batman',
  'Superman',
];
// heroes.length === 2 (not 3)

Так что, скорее всего, если вы используете ES5 и выше, вам не нужно об этом беспокоиться.

Я думал, что они были стандартными, но IE8 вырвался после столкновения с ним - конечно, IE, не поддерживающий что-то, вряд ли означает, что это не стандарт.

Опять же, это вопрос поддержки ECMAScript 5. IE8 не поддерживает ECMAScript 5 (только IE9 и выше)

Я очень рекомендую взглянуть на устаревшую документацию ES5 Airbnb https://github.com/airbnb/javascript/blob/es5-deprecated/es5/README.md#commas

Я также рекомендовал бы документы Mozilla:
https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Trailing_commas

garrettmac
источник
1

На Chrome 52:

[1,].length --> 1
[1,2,].length --> 2
[].length --> 0 
[,].length --> 1    <<<<=== OUHHHHH !!!!

Мне просто не нравятся запятые. Люди обычно используют их в проектах с открытым исходным кодом, чтобы избежать стирания строки, написанной другим коммиттером. Смотрите тот же вопрос в Python: https://stackoverflow.com/a/11597911/968988

Николас Зозол
источник
13
Почему «ОХХХХХХ»? Что еще ты ожидал там, если не 1? У вас явно есть «элемент» перед запятой, как [1,] (это длина: 1).
Fygo
Почему «ОХХХХХХ»? потому что я не ожидаю ничего от кода, который не понимаю, не читая RFC. И да, это работает так же, как и [1,]перед запятой. Но [,]там до и после запятой столько же. Так как я не понимаю в [,]одиночку, я не думаю, что использование [1,]это хорошая идея.
Николас Зозол