发布于2026-07-23 阅读(0)
扫一扫,手机访问
写 Ja vaScript 的时候,因为数据类型判断不准确而出错,这种经历不少开发者都有过。比如下面这段代码:
function calculate(a, b) {
return a + b;
}
// 我以为是 10 + 20 = 30
calculate(10, 20); // 结果 30 对的
// 实际上用户输入的是字符串和数字
calculate("10", 20); // 结果为 "1020"
所以说,数据类型判断这件事,真的不能马虎。Ja vaScript 提供了几种判断数据类型的方法,各有各的适用场景。
这是最常用的类型判断方法,不过有一些局限性,需要留意:
typeof 42; // "number"
typeof "hello"; // "string"
typeof true; // "boolean"
typeof undefined; // "undefined"
typeof null; // "object" (历史遗留问题)
typeof {}; // "object"
typeof []; // "object"
typeof function(){}; // "function"
typeof Symbol(); // "symbol"
typeof 42n; // "bigint"
局限性:
nullfunctiontypeof 适合判断基本类型,但遇到对象类型就力不从心了用于检测构造函数的 prototype 属性是否出现在对象的原型链中:
[] instanceof Array; // true
{} instanceof Object; // true
new Date() instanceof Date; // true
function(){} instanceof Function; // true
// 继承关系,数组也是对象
[] instanceof Object; // true
instanceof 的局限性:
// 基本类型用不了 42 instanceof Number; // false "hello" instanceof String; // false
在跨 iframe 或不同 window 环境下可能失效(因为构造函数不同)
这是最准确、最可靠的方法,能识别所有内置类型!
Object.prototype.toString.call(42); // "[object Number]"
Object.prototype.toString.call("hello"); // "[object String]"
Object.prototype.toString.call(true); // "[object Boolean]"
Object.prototype.toString.call(null); // "[object Null]"
Object.prototype.toString.call(undefined); // "[object Undefined]"
Object.prototype.toString.call([]); // "[object Array]"
Object.prototype.toString.call({}); // "[object Object]"
Object.prototype.toString.call(function(){}); // "[object Function]"
Object.prototype.toString.call(Symbol()); // "[object Symbol]"
Object.prototype.toString.call(42n); // "[object BigInt]"
封装一个实用的工具函数:
function getRealType(value) {
return Object.prototype.toString.call(value)
.slice(8, -1) // 截取"[object "和"]"之间的内容
.toLowerCase(); // 转为小写,更友好
}
console.log(getRealType([])); // "array"
console.log(getRealType(null)); // "null"
console.log(getRealType({})); // "object"
console.log(getRealType(new Date())); // "date"
对于一些特殊类型,Ja vaScript 提供了专门的判断方法:
Array.isArray([]); // true
Array.isArray({}); // false
Array.isArray("123"); // false
// 注意区别!
isNaN("hello"); // true ← 字符串不是数字,但这样判断容易误解
Number.isNaN("hello"); // false ← 更准确:只有真正的NaN才返回true
Number.isNaN(NaN); // true
Number.isFinite(42); // true
Number.isFinite(Infinity); // false ← 无穷大不是有限数字
Number.isFinite("42"); // false ← 字符串不是数字
在实际开发中的应用:
function safeAdd(a, b) {
// 确保两个参数都是数字类型
if (typeof a !== 'number' || typeof b !== 'number') {
throw new Error('参数必须是数字');
}
return a + b;
}
safeAdd(1, 2); // 3
safeAdd(1, "2"); // 报错:参数必须是数字
function processData(data) {
// getRealType方法在第3点Object.prototype.toString.call()中有写
const type = getRealType(data);
switch(type) {
case 'array':
return data.map(item => item * 2);
case 'object':
return Object.keys(data).length;
case 'string':
return data.toUpperCase();
case 'number':
return data * 2;
default:
return '不支持的数据类型';
}
}
console.log(processData([1, 2, 3])); // [2, 4, 6]
console.log(processData("hello")); // "HELLO"
console.log(processData({a: 1, b: 2})); // 2
| 场景 | 推荐方法 | 示例 |
|---|---|---|
| 判断基本类型 | typeof | typeof "hello" === "string" |
| 判断数组 | Array.isArray() | Array.isArray([]) |
| 判断自定义对象 | instanceof | obj instanceof MyClass |
| 精确类型判断 | Object.prototype.toString.call() | 见上文工具函数 |
| 特殊值判断 | 专用方法 | Number.isNaN(), Number.isFinite() |
售后无忧
立即购买>office旗舰店
售后无忧
立即购买>office旗舰店
售后无忧
立即购买>office旗舰店
售后无忧
立即购买>office旗舰店
正版软件
正版软件
正版软件
正版软件
正版软件
1
2
3
7
8