Подтвердить что ты не робот

Является ли localStorage.getItem('item') лучше, чем localStorage.item или localStorage ['item']?

Недавно я спросил вопрос о LocalStorage. Использование JSON.parse(localStorage.item) и JSON.parse(localStorage['item']) не работало, чтобы вернуть NULL, когда элемент еще не был установлен.

Однако JSON.parse(localStorage.getItem('item') действительно работал. И получается, JSON.parse(localStorage.testObject || null) также работает.

Один из комментариев в основном сказал, что localStorage.getItem() и localStorage.setItem() всегда должны быть предпочтительными:

Геттер и сеттер обеспечивают последовательную стандартизацию и совместимый с кроссбраузером способ работы с LS api и всегда должен предпочтительнее других способов. - Christoph

Мне понравилось использовать сокращенные точечные и скобковые обозначения для localStorage, но мне любопытно узнать, что другие принимают это. Является ли localStorage.getItem('item') лучше, чем localStorage.item или localStorage ['item'] ИЛИ если они работают, это сокращенные обозначения в порядке?

4b9b3361

Ответ 1

Как прямой доступ к свойству (localStorage.item или localStorage['item']), так и использование функционального интерфейса (getItem('item')) работают нормально. Оба стандарта и кросс-браузер совместимы. * Согласно спецификации:

Имена поддерживаемых свойств объекта Storage - это ключи каждой пары ключ/значение, присутствующей в данный момент в списке, связанном с объектом, в том порядке, в котором ключи были в последний раз добавлены в область хранения.

Они просто ведут себя по-разному, когда не найдено пары ключ/значение с запрошенным именем. Например, если ключ 'item' не существует, var a = localStorage.item; приведет a undefined, тогда как var a = localStorage.getItem('item'); приведет к, имеющему значение a null. Как вы обнаружили, undefined и null не являются взаимозаменяемыми в JavaScript/EcmaScript. :)

РЕДАКТИРОВАТЬ: Как указывает Кристоф в своем ответе, функциональный интерфейс является единственным способом надежного хранения и извлечения значений под ключами, равными предопределенным свойствам localStorage. (Есть шесть из них: length, key, setItem, getItem, removeItem и clear.) Так, например, всегда будет работать следующее:

localStorage.setItem('length', 2);
console.log(localStorage.getItem('length'));

В частности, обратите внимание, что первый оператор не повлияет на свойство localStorage.length (за исключением, возможно, его увеличения, если в localStorage уже не было ключа 'length'). В этом отношении спецификация кажется внутренне противоречивой.

Однако следующее, вероятно, не будет делать то, что вы хотите:

localStorage.length = 2;
console.log(localStorage.length);

Интересно, что первый - это неиспользование в Chrome, но оно синонимично с функциональным вызовом в Firefox. Второй всегда будет регистрировать количество ключей, присутствующих в localStorage.

*Это верно для браузеров, которые в первую очередь поддерживают веб-хранилище.(Это относится практически ко всем современным настольным и мобильным браузерам.) Для сред, которые имитируют локальное хранилище с использованием файлов cookie или других методов, поведение зависит от используемой прокладки.Несколько полифилов для localStorage можно найти здесь.

Ответ 2

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

Объект хранения является довольно особенным, это объект, который обеспечивает доступ к списку пар ключ/значение. Таким образом, это не обычный объект или массив.

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

С массивом вы можете сделать:

var a = [1,2,3,4];
a.length // => 4
a.length = 2;
a // => [1,2]

Здесь у нас есть первая причина использовать геттеры/сеттеры. Что если вы хотите установить элемент с именем length?

localStorage.length = "foo";
localStorage.length  // => 0
localStorage.setItem("length","foo");
// the "length" key is now only accessable via the getter method:
localStorage.length  // => 1
localStorage.getItem("length") // => "foo"

С другими членами объекта Storage это еще более критично, так как они доступны для записи, и вы можете случайно перезаписать такие методы, как getItem. Использование методов API предотвращает любую из этих возможных проблем и обеспечивает согласованный интерфейс.

Также интересным моментом является следующий абзац в спецификации (выделенный мной):

Методы setItem() и removeItem() должны быть атомарными относительно ошибки. В случае неудачи метод ничего не делает. То есть изменения в области хранения данных должны быть либо успешными, либо область хранения данных не должна изменяться вообще.

Теоретически не должно быть никакой разницы между получателями/установщиками и доступом [], но вы никогда не знаете...

Ответ 3

Я знаю, что это старый пост, но поскольку никто не упоминал о производительности, я установил некоторые тесты JsPerf для его сравнения, а также как последовательный интерфейс getItem и setItem также последовательно быстрее, чем использование точечной нотации или скобок а также гораздо легче читать.

Вот мои тесты на JsPerf

Ответ 4

Как уже упоминалось, практически нет разницы, кроме несуществующего ключа. разница в производительности варьируется в зависимости от того, какой браузер/ОС вы используете. Но на самом деле это не так.

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