Почему в JavaScript есть значение "null"?

В JavaScript есть два значения, которые в основном говорят "Я не существую" - undefined и null.

Свойство, которому программист ничего не назначил, будет undefined, но для того, чтобы свойство стало null, ему должно быть явно присвоено null.

Я подумал, что существует необходимость в null, потому что undefined является примитивным значением и null объектом. Это не так, даже если typeof null даст 'object': на самом деле оба являются примитивными значениями - это означает, что из функции конструктора нельзя возвращать undefined и null, поскольку оба будут преобразованы в пустой объект (один должен выдать ошибку для объявления отказа в конструкторах).

Они также оценивают значение false в булевых контекстах. Единственное реальное различие, о котором я могу думать, состоит в том, что вы оцениваете значение NaN, а другое - в 0 в числовых контекстах.

Итак, почему существуют undefined и null, если это просто путает программистов, которые неправильно проверяют null при попытке выяснить, установлено ли свойство или нет?

edit: Я хотел бы знать, есть ли у кого-нибудь разумный пример, где нужно использовать null, который не может быть выражен с помощью undefined.

edit2 + 3. Таким образом, общий консенсус, по-видимому, заключается в том, что undefined означает "нет такого свойства", а null означает, что свойство существует, но не имеет значения ".

Я мог бы с этим справиться, если бы реализация JavaScript действительно обеспечивала выполнение этого поведения, но undefined является вполне допустимым примитивным значением, поэтому его можно легко присвоить существующим свойствам для разрыва этого контракта. Поэтому, если вы хотите убедиться, что существует свойство, вы должны использовать оператор in или hasOwnProperty() в любом случае. Итак, еще раз: какое практическое использование для отдельных значений для undefined и null?

Я использую undefined, когда хочу отключить значения свойств, которые больше не используются, но которые я не хочу использовать delete. Должен ли я использовать null вместо этого?

Ответ 1

Вопрос не в том, "почему в JS есть нулевое значение" - на большинстве языков есть нулевое значение, и оно обычно считается очень полезным.

Вопрос: "Почему в JS есть значение undefined. Основные места, где он используется:

  • когда вы объявляете 'var x;' но не присваивать ему, x содержит undefined;
  • когда ваша функция получает меньше аргументов, чем объявляет;
  • при доступе к несуществующему объекту.

'null', безусловно, сработал бы точно также для (1) и (2) *. (3) должен действительно выбросить исключение сразу, а тот факт, что он этого не делает, вместо этого вернет этот странный "undefined", который не удастся позже, является большим источником сложности отладки.

*: вы также можете утверждать, что (2) должно генерировать исключение, но тогда вам нужно будет предоставить более эффективный и более явный механизм аргументов по умолчанию/переменной.

Однако у JavaScript не были изначально исключения или какой-либо способ спросить объект, если у него был член под определенным именем - единственный способ (и иногда еще) - доступ к члену и просмотр того, что вы получаете. Учитывая, что "нуль" уже имел цель, и вы вполне можете захотеть установить для него член, потребовалось другое внеполосное значение. Итак, у нас есть "undefined", это проблематично, как вы указываете, и это еще одна отличная функция JavaScript, с которой мы никогда не сможем избавиться.

Я действительно использую undefined, когда хочу отключить значения свойств, которые больше не используются, но которые я не хочу удалять. Должен ли я использовать null вместо?

Да. Keep 'undefined' как специальное значение для сигнализации, когда другие языки могут вызывать исключение.

'null', как правило, лучше, за исключением некоторых интерфейсов IE DOM, где установка значения "null" может привести к ошибке. Часто в этом случае настройка на пустую строку имеет тенденцию работать.

Ответ 2

Лучше всего описано здесь, но в итоге:

undefined - это отсутствие типа и значения, а null - отсутствие значения.

Кроме того, если вы делаете простые сравнения "==", вы правы, они выходят одинаково. Но попробуйте ===, в котором сравниваются как тип, так и значение, и вы заметите разницу.

Ответ 3

Я не думаю, что есть какая-то причина иметь как null, так и undefined, потому что единственная причина, которую предложили многие люди ( "undefined означает, что нет такой переменной/свойства" ) недействительна, по крайней мере в JavaScript. undefined не может сказать вам, существует или нет свойство variable/.

console.log(foo);               // "ReferenceError: foo is not defined"
                                // foo does not exist
var foo;
console.log(foo);               // "undefined", a different response
console.log(foo === undefined); // "true", but it does exist

var obj = {};
console.log(obj.hasOwnProperty("foo")); // "false", no such property
obj.foo = undefined;
console.log(obj.hasOwnProperty("foo")); // "true", it exists and has the value "undefined"
console.log(obj.foo === undefined);     // "true", but it does exist

obj.bar = "delete me";
obj.bar = undefined;
console.log(obj.hasOwnProperty("bar")); // "true", not actually deleted
delete obj.bar;
console.log(obj.hasOwnProperty("bar")); // "false", deleted

Как вы можете видеть, проверка foo === undefined не говорит вам, существует ли foo, а установка obj.bar = undefined фактически не удаляет bar.

Возможно, оригинальное намерение автора JavaScript состоит в том, что undefined должно представлять "несуществование". Однако реализация не получилась.

Ответ 4

Вполне возможно, что и то, и другое. Например, если вы запрашиваете WMI, вполне возможно иметь свойства возврата класса, которые имеют нулевое значение. Они определены, они просто имеют значение null в то время.

Ответ 5

Я думаю, что ваш вывод о том, что JavaScript определяет undefined как "нет такого свойства" и null, поскольку "свойство не имеет значения" совершенно правильно. И на языке, который динамичен как JavaScript, это очень важное различие. Использование утиной печати означает, что нам нужно иметь возможность различать свойство, не существующее и не имеющее значения. Это наш основной способ получения информации о типе. в статически типизированном языке существует определенное различие между полем, равным нулю, и полем, не существующим. В JavaScript это ничем не отличается. Однако он проверяется во время выполнения и может быть изменен до этого времени.

Мне нужно согласиться с тем, что реализация странная, поскольку много раз различие размыто. Однако я считаю, что в JavaScript важное значение имеет различие. И возможность назначения undefined имеет важное значение.

Я помню, как недавно прочитал сообщение в блоге о онлайн-RPG, написанном на JavaScript. В нем использовались примеры, когда объекты были созданы как копии существующих экземпляров, а не прототипов (классов, функций и т.д.) И затем были изменены. Это действительно заставило меня понять, насколько мощным может быть undefined при изменении существующих объектов, но я не могу вспомнить, кто его написал.

Ответ 6

Семантически они означают разные вещи. Тип null имеет ровно одно значение в своем домене, null, и этому свойству может быть присвоено свойство. Undefined представляет собой отличное отсутствие назначенного значения.

Ответ 7

Как программист на Java, я вижу огромную разницу между undefined и null. Кодирование JavaScript не так много, потому что JavaScript не сильно типизирован, а различия между undefined и null размыты автоматическими преобразованиями, которые часто выполняются во время выполнения. Кстати, я часто пользуюсь этими преобразованиями; они делают мой JS-код более компактным и удобочитаемым.

Чтобы ответить на ваш вопрос, undefined означает, что значение никогда не было установлено. Практически говоря, это обычно указывает на ошибку. Если yourObject.property undefined, это означает, что вы почему-то не задали свойство, или я ищу что-то, чего не существует вообще. Это реальная проблема при работе над проектом с несколькими кодерами.

null означает, что "no value" явно задано. Практически говоря, вы рассказываете мне что-то об этом свойстве, возможно, что оно не используется в этом контексте или что значение еще не определено.

В Java попытки получить доступ к полю undefined всегда будут приводить к исключению. Фактически, компилятор может быть сделан, чтобы предупредить вас об этом в вашем коде.

Ответ 8

Попробуйте этот пример:

<html>
<head>
    <script type="text/javascript">
        function ShowObjProperties(obj) {
            var property, propCollection = "";

            for(property in obj) {
                propCollection += (property + ": " + obj[property] + "\n");
            }

            alert(propCollection);
        }

        var obj = {
            userid: 3,
            name: 'me!',
            speak: function() { alert('Hi! My name is ' + this.name + ' and my ID is ' + this.userid + '.'); }
        }

        //Shows all properties
        ShowObjProperties(obj);

        //The Speak function is no longer in the list!
        delete obj.speak;
        alert(typeof obj.speak);
        ShowObjProperties(obj);

        //The UserID is still listed, it just has no value!
        obj.userid = null;
        ShowObjProperties(obj);
    </script>
</head>
<body>

</body>
</html>

Я думаю, что здесь есть очень реальное использование для двух разных типов.

Ответ 9

В чем дело, это динамическая природа javascripts.

Вещи могут быть undefined, чтобы их можно было добавить позже. Возможно, именно поэтому javascript настолько мощный и расширяемый.

Ответ 10

null - красивый

как и все другие типы Live Script.

cite: В JavaScript есть два значения, которые в основном говорят: "Я не exist '- undefined и null.

Почему вы хотите сказать неправильные вещи?!

"null" - это "пустой объект", как "0" - это "пустое число". 0, ничего не значит, что он существует как тип числа. null, конечно, также пуст, но "это" и это хорошо определенная вещь типа объекта.

Обычно говорить об этих вещах как о "типах", когда их нет. На самом деле это "категории". Но это уже сейчас.

Так будет придерживаться этого, чтобы сказать, что "null" - это Тип Объекта без Добра. И "null" говорит: "Я очень много [!], Но у меня нет содержания в моем роде".

В то время как undefined не хватает и типа, и вида, где undefined также является его определением типа. Тип типа undefined становится его отличительной типологией. Что-то вроде [ничего не существует и как вы определяете "ничего"?] Вопрос.

cite: undefined, а null может быть возвращен из функции-конструктора, так как оба будут конвертером в пустой объект

Вам удалось еще раз сказать неправильную вещь. Конечно, нет, "undefined" - это не объект, его простой токен, который мы, люди, понимаем; но вопреки этому нулевому - и он говорит вам, что: его Тип правильный, но вид, который вы ищете, не содержится в нем или, по крайней мере, не в это время. Приходите к нам позже, когда мы помещаем\присваиваем некоторый объект в\ему.

cite: Единственное реальное различие, о котором я могу думать, это то, что человек оценивает NaN, а другой - 0 в числовых контекстах.

Это делает всю суть их основного различия, как уже упоминалось: undefined - простой токен, и поскольку он составлен из того же "генетического" материала, что и его дальние родственники: строки, [+ undefined] операция будет утка-преобразовать ее в NaN, аналогично, нуль, конечно, превратится в правильный вид 0\Number вместо этого, а в отличие от undefined, который превратится в строку (! которая не пуста!), и именно поэтому он дает NaN вместо этого. Где: + undefined → + "undefined" → NaN. Поскольку числовой контекст ожидает явного значения.

В то время как булевский контекст ожидает ссылки - не находит ничего для преобразования и дает "false".

Разрежьте теперь...

cite: Итак, еще раз: что практическое использование для отдельных значений для undefined и null?

Я попытаюсь дать вам только два эмпирических примера и надеюсь, что хватит

oElement.onclick >> null

//означает - свойство существует; его ожидаемое значение относится к типу: объект и что oElement поддерживает событие onclick!

oElement.innerText >> ""

//означает - свойство существует; его ожидаемое значение имеет тип: String, что означает, что oElement поддерживает свойство innerText.

в обоих случаях - если вы получили "undefined" , это означает, что свойство не существует; не поддерживается или имеет неправильную реализацию (ua vendor).

Оставайтесь морозом и получайте удовольствие.

Ответ 11

это важная языковая функция, если вы завершаете свою программу вокруг выделенной парадигмы javascript.

// a key exists as a placeholder for something
if(obj[name] === null) 
// no key exists int eh hashtable that is in this object
if(obj[name] === undefined)

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

filter_func_pt = {
  date:function(d){ return Math.round(d.getTime()/1000);},
  user: null,
}

function transform(obj){
    var ret = {};
    for( var prop in obj){
       var f = filter_func_pt[prop];
       if(f)
          ret[prop] = f(obj);
       else if(filter_func_pt[prop] === null)
         continue;
       else
         ret[prop] == obj;
    }
  return ret;
}

var a = {
   date: new Date(),
   user: 'sam'
   votes: [23, 41, 55] 
};

var b = transform(a);

/* b = {
 *    date: 1298582417
 *    votes: [23, 41, 55]
 * }
 */

в приведенном выше коде ключевое слово null и сервер undefined очень четкие и разные цели. поиск, который не найден в объекте filter_func_pt, который возвращает undefined, означает добавление свойства в возвращаемый объект как есть, тогда как нулевое значение указывает, что значение должно быть удержано и не добавлено, а также наличие какого-либо истинного значения в этом случае представляет собой функцию, используемую для преобразования значения перед добавлением его в объект ret.