В JSON, Почему каждое имя цитируется?
Спецификация JSON говорит, что JSON - это объект или массив. В случае объекта
Структура объекта представлена в виде пары фигурных скобок окружающие ноль или несколько пар имен/значений (или членов). Имя - это строка....
И позже спецификация говорит, что строка окружена кавычками.
Почему?
Таким образом,
{"Property1":"Value1","Property2":18}
а не
{Property1:"Value1",Property2:18}
Вопрос 1: почему бы не разрешить имя в парах имя/значение быть некотируемыми идентификаторами?
Вопрос 2: Существует ли семантическая разница между двумя представлениями выше, когда оценивается в Javascript?
Ответы
Ответ 1
Вопрос 1: почему бы не разрешить имя в парах имя/значение быть некотируемыми идентификаторами?
Философия дизайна JSON - "Держите его просто"
"Имена котировок с "
" намного проще, чем "Вы можете указывать имена с помощью "
или '
, но вам не нужно, если они не содержат определенных символов (или комбинаций символов, которые могли бы это ключевое слово), а '
или "
может потребоваться указать в зависимости от выбранного разделителя.
Вопрос 2: Существует ли семантическая разница между двумя представлениями выше, когда оценивается в Javascript?
Нет. В JavaScript они идентичны.
Ответ 2
Я оставляю цитату из презентации, которую Даглас Крокфорд (создатель стандарта JSON) дал Yahoo.
Он рассказывает о том, как он открыл JSON, и среди прочего, почему он решил использовать цитируемые ключи:
.... Это было тогда, когда мы обнаружили проблема с некотируемым именем. Получается ECMA Script 3 имеет запрет текстовой политики. Зарезервированные слова должны быть цитируется в ключевой позиции, которая действительно неприятность. Когда я обошел сформулировать это в стандарт, я не хотел, чтобы все зарезервированные слова в стандарте, потому что это выглядело бы очень глупо.
В то время я пытался убедить люди: да, вы можете написать приложений в JavaScript, это на самом деле собирается работать, и это хорошо язык. Тогда я не хотел говорить, в то же время: и посмотрите на это действительно глупо, что они сделали! Так что я решил вместо этого дать просто ключи.
Таким образом, нам не нужно кто-нибудь о том, как это происходит.
Вот почему, по сей день, ключи цитируются в JSON.
Вы можете найти полное видео и транскрипцию здесь.
Ответ 3
Оба идентификатора :
и пробелы разрешены в идентификаторах. Без кавычек это может вызвать двусмысленность при попытке определить, что именно составляет идентификатор.
Ответ 4
В javascript-объектах можно использовать как хэш-хэш-таблицу с парами ключей.
Однако, если у вашего ключа есть символы, которые javascript не может обозначать как имя, он будет терпеть неудачу при попытке доступа к нему как к объекту, а не к ключу.
var test = {};
test["key"] = 1;
test["#my-div"] = "<div> stuff </div>";
// test = { "key": 1, "#my-div": "<div> stuff </div>" };
console.log(test.key); // should be 1
console.log(test["key"]); // should be 1
console.log(test["#my-div"]); // should be "<div> stuff </div>";
console.log(test.#my-div); // would not work.
В идентификаторах иногда могут быть символы, которые не могут быть оценены как токен/идентификатор в javascript, поэтому лучше всего поместить все идентификаторы в строки для согласованности.
Ответ 5
Я думаю, что правильный ответ на вопрос Cheeso заключается в том, что реализация превзошла документацию. Он больше не требует строки в качестве ключа, а скорее что-то еще, которое может быть либо строкой (т.е. Цитируемой), либо (возможно) тем, что может использоваться как имя переменной, которое, я думаю, означает начало с буквы, или $и включать только буквы, цифры и $и _.
Я хотел упростить остальные для следующего человека, который посещает этот вопрос с той же идеей, что и я. Здесь мясо:
Имена переменных не интерполируются в JSON при использовании в качестве ключевого объекта (спасибо Friedo!)
Бретон, используя "идентификатор" вместо "ключа", писал, что "если идентификатор является зарезервированным словом, он интерпретируется как это слово, а не как идентификатор". Это может быть правдой, но я пробовал это без проблем:
var a = {do:1,long:2,super:3,abstract:4,var:5,break:6,boolean:7};
a.break
= > 6
Об использовании кавычек, Quentin написал "... но вам этого не нужно, если только [ключ] содержит определенные символы (или комбинации символов, которые сделали бы его ключевым словом)"
Я обнаружил, что первая часть (определенные символы) истинна, используя знак @(на самом деле, я думаю, что $и _ являются единственными символами, которые не вызывают ошибку):
var a = {[email protected]:1};
= > Ошибка синтаксиса
var a = {"[email protected]":1};
a['[email protected]']
= > 1
но в скобках о ключевых словах, как я показал выше, неверно.
То, что я хотел, работает, потому что текст между открытием {и двоеточием или между запятой и двоеточием для последующих свойств используется как некорректная строка, чтобы сделать ключ объекта или, как сказал Фридо, имя переменной интерполируется:
var uid = getUID();
var token = getToken(); // Returns ABC123
var data = {uid:uid,token:token};
data.token
= > ABC123
Ответ 6
Если json описывает объекты, то на практике вы получаете следующие
var foo = {};
var bar = 1;
foo["bar"] = "hello";
foo[bar] = "goodbye";
значит,
foo.bar == "hello";
foo[1] == "goodbye" // in setting it used the value of var bar
поэтому даже если ваши примеры производят одинаковый результат, их эквиваленты в "сыром коде" не будут. Может быть, почему??? не знаю, просто идея.