Undefined 类型 、Null 类型 - JavaScript 笔记

590 阅读3分钟

Undefined 类型

Undefined (读音 英 [ʌndɪ'faɪnd]) 类型是只有一个值的数据类型,这个特殊的值是 undefined。在使用 var 声明变量但未对其加以初始化化时,这个变量的值就是 undefined,例如:

var message;
console.log(message == undefined);    // 输出:true
console.log(message === undefined);   // 输出:true

这个例子只声明了变量 message,但未对其进行初始化。比较这个变量于 undefined 字面量,结果表明它们是相等的。这个例子与下面的例子是等价的:

var message = undefined;
console.log(message == undefined);   // 输出:true
console.log(message === undefined);  // 输出:true

这个例子使用 undefined 值显式初始化了变量 message。但我们没有必要这样做,因为未经初始化的值默认就会取得 undefined 值。

不过,包含 undefined 值的变量与尚未定义的变量还是不一样的。例如:

var message;    // 这个变量声明之后默认取得了 undefined 值

// 下面这个变量并没有声明
// var age;

console.log(message);   // 输出:undefined
console.log(age);       // 抛出异常:age is not defined

运行以上代码,第一个输出变量 message 的值:undefined。而第二个由于传递给 console.log() 函数的是尚未声明的变量 age , 会导致一个错误。对于尚未声明过的变量,只能执行一项操作,即使用 typeof 操作符检测其数据类型。

然而,令人困惑的是:对未初始化的变量执行 typeof 操作符会返回 undefined 值,而对未声明的变量执行 typeof 操作符同样也会返回 undefined 值。例如:

var message;    // 这个变量声明之后默认取得了 undefined 值

// 下面这个变量并没有声明
// var age

console.log(typeof message);   // 输出:undefined
console.log(typeof age);       // 输出:undefined

结果表明,对未初始化和未声明的变量执行 typeof 操作符都返回了 undefined 值;这个结果有其逻辑上的合理性。因为虽然这两种变量从技术角度看有本质区别,但实际上无论对哪种变量也不可能执行真正的操作。

即便未初始化的变量会自动被赋予 undefined 值,但显式地初始化变量依然是明智的选择。如果能够做到这一点,那么当 typeof 操作符返回 “undefined” 值时,我们就知道被检测的变量还没有被声明,而不是尚未初始化。

Null 类型

Null (读音 英 [nʌl]) 类型是只有一个值的数据类型,这个特殊的值是 null。从逻辑角度来看,null 值表示一个空对象指针,而这也正是使用 typeof 操作符检测 null 值时会返回 “object” 的原因,例如:

console.log(typeof null)    // 输出:object

var car = null;
console.log(typeof car)     // 输出:object

如果定义的变量准备在将来用于保存对象,那么最好将该变量初始化为 null , 而不是其它值。这样,只要直接检查 null 值就可以知道相应的变量是否已经保存了一个对象的引用,例如:

if (car != null) {
    // 对 car 对象执行某些操作
}

总结

实际上,undefined 值是派生子 null 值的,因此 ECMA-262 规定对它们的相等性测试要返回 true;例如:

console.log(null == undefined)  // 输出:true

console.log(null === undefined) // 输出:false

以上,位于 null 和 undefined 之间的相等操作符( == )总是返回 true,不过要注意的是,这个操作符出于比较的目的会转换其操作数。

尽管 null 和 undefined 有这样的关系,但它们的用途完全不同。如前所述,无论在什么情况下都没有必要把一个变量的值显式地设置为 undefined,可是同样的规则对 null 却不适用。换句话说,只要意在保存对象的变量还没有真正保存对象,就应该明确地让该变量保存 null 值。这样做不仅可以体现 null 作为空对象指针的惯例,而且也有助于进一步区分 null 和 undefined。