TypeScript - null 与 undefined 的区别
你好,有抱负的程序开发者们!今天,我们将深入探讨一个经常让初学者感到困惑的激动人心的话题:TypeScript 中的 null
和 undefined
之间的区别。如果你现在感到有些不知所措,别担心——我记得我第一次遇到这些概念时,我也感到很困惑!但到了这节课的结尾,你将成为区分这两个特殊值的专家。让我们开始吧!
什么是 null?
在 TypeScript(和 JavaScript)中,null
是一个特殊值,表示故意没有对象值。这就像说:“嘿,这里应该有东西,但现在,什么都没有。”
让我们看一些例子来更好地理解这一点:
let myPet: string | null = null;
console.log(myPet); // 输出:null
// 代码稍后...
myPet = "Fluffy";
console.log(myPet); // 输出:Fluffy
在这个例子中,我们声明了一个可以是字符串或 null 的变量 myPet
。最初,我们将其设置为 null
,表示我们还没有宠物。稍后,当我们得到一个宠物时,我们将名字 "Fluffy" 赋值给 myPet
。
这里还有一个例子:
function findUser(id: number): { name: string } | null {
// 想象我们在搜索数据库
if (id === 1) {
return { name: "Alice" };
} else {
return null;
}
}
let user = findUser(1);
console.log(user); // 输出:{ name: "Alice" }
user = findUser(2);
console.log(user); // 输出:null
在这种情况下,我们的 findUser
函数返回一个用户对象或 null
,如果没有找到用户。这是一种常见的编程模式——使用 null
来表示搜索或操作没有产生结果。
什么是 undefined?
现在,让我们来谈谈 undefined
。这个特殊值表示一个已声明但尚未赋值的变量。就像一个空盒子——它存在,但里面什么都没有。
以下是一些说明 undefined
的例子:
let myName: string;
console.log(myName); // 输出:undefined
// 代码稍后...
myName = "John";
console.log(myName); // 输出:John
function greet(name?: string) {
console.log(name);
}
greet(); // 输出:undefined
greet("Alice"); // 输出:Alice
在第一部分,我们声明了 myName
但没有赋值。TypeScript 自动给它赋值 undefined
。稍后,我们赋了一个值,它就不再是 undefined 了。
在 greet
函数中,我们使用了一个可选参数。如果我们不提供参数调用函数,name
参数将是 undefined
。
以下是你可能会遇到 undefined
的另一种情况:
let person = {
name: "Bob",
age: 30
};
console.log(person.name); // 输出:Bob
console.log(person.job); // 输出:undefined
在这种情况下,person.job
是 undefined
,因为我们从未为我们的 person
对象定义 job
属性。
Null 与 Undefined:关键区别
现在我们已经单独探讨了 null
和 undefined
,让我们将它们并排放置,以更好地理解它们的区别。
方面 | null | undefined |
---|---|---|
含义 | 故意没有对象值 | 变量已声明但未赋值 |
类型 | 对象 | Undefined |
在 JSON 中 | 有效 | 无效 |
默认函数参数 | 不用作默认值 | 用作可选参数的默认值 |
相等性 | null == undefined (true), null === undefined (false) | undefined == null (true), undefined === null (false) |
让我们看一些代码示例来阐述这些区别:
// 类型检查
console.log(typeof null); // 输出:"object"
console.log(typeof undefined); // 输出:"undefined"
// JSON 序列化
console.log(JSON.stringify({ a: null })); // 输出:{"a":null}
console.log(JSON.stringify({ a: undefined })); // 输出:{}
// 默认函数参数
function sayHello(name: string = "World") {
console.log(`Hello, ${name}!`);
}
sayHello(); // 输出:Hello, World!
sayHello(undefined); // 输出:Hello, World!
sayHello(null); // 输出:Hello, null!
// 相等性
console.log(null == undefined); // 输出:true
console.log(null === undefined); // 输出:false
在实践中,选择 null
还是 undefined
通常取决于个人或团队的偏好。然而,了解这些区别可以帮助你编写更精确且无错误的代码。
以下是一个最后的例子来概括所有内容:
function processUser(user: { name: string, age?: number } | null | undefined) {
if (user === null) {
console.log("用户显式设置为 null");
} else if (user === undefined) {
console.log("用户未提供");
} else {
console.log(`处理用户:${user.name},年龄:${user.age ?? "未知"}`);
}
}
processUser(null); // 输出:用户显式设置为 null
processUser(undefined); // 输出:用户未提供
processUser({ name: "Alice" }); // 输出:处理用户:Alice,年龄:未知
processUser({ name: "Bob", age: 30 }); // 输出:处理用户:Bob,年龄:30
这个函数演示了我们在现实世界的场景中如何可能不同地处理 null
、undefined
和有效的用户对象。
就这样!你刚刚学习了 TypeScript 中的 null
和 undefined
的来龙去脉。记住,熟能生巧,所以不要害怕在你的代码中实验这些概念。快乐编码,愿你的变量总是有意地设置为 null 或 undefined!
Credits: Image by storyset