Skip to content

类型判定

Object.prototype.toString.call() 用它

typeof

  • 是个运算符。
  • 能判断类型的所有结果:9情况,8种返回值。
类型结果
Undefined"undefined"
Null"object"
Boolean"boolean"
Number"number"
String"string"
BigInt"bigint"
Symbol"symbol"
Function"function"
其他任何对象"object"

注意

typeof 对象类型的值的类型不能作出准确判断,能准确判断出基本数据类型的值。

instanceof

javascript
object instanceof constructor
object instanceof constructor
  • object:实例对象

  • constructor:构造函数

  • 描述:用于检测构造函数的 prototype 属性是否出现在某个实例对象的原型链上。

检测 constructor 的 prototype 否在存在于object 的原型链上

javascript
const myDate = new Date();
myDate instanceof Date; // 返回 true
myDate instanceof Object; // 返回 true
myDate instanceof String; // 返回 false
const myDate = new Date();
myDate instanceof Date; // 返回 true
myDate instanceof Object; // 返回 true
myDate instanceof String; // 返回 false

注意

  1. 原型链可可以被修改,导致检测结果不准确。

  2. undefined和null没有构造函数,使用 instanceof 会抛出异常。

  3. instanceof 一般用于判断对象,无法很好的满足基本数据类型的判定。

constructor不推荐

  • 描述:返回实例对象的构造函数
javascript
console.log((1).constructor === Number) // true
console.log([1, 2, 3].constructor === Array) // true
console.log(undefined.constructor === Array) // 报错
console.log((1).constructor === Number) // true
console.log([1, 2, 3].constructor === Array) // true
console.log(undefined.constructor === Array) // 报错

注意

null,undefined 没有构造函数,自然也就访问不到该属性,因此不能使用此属性来判断。

constructor 可以被改写,所以不一定准确。

Symbol.toStringTag

  • 描述
    1. Symbol.toStringTag 内置通用(well-known)symbol 是一个字符串值属性,用于创建对象的默认字符串描述。它由 Object.prototype.toString() 方法内部访问。
    2. 大多数内置的对象提供了它们自己的 [Symbol.toStringTag] 属性。
    3. toStringTag 适用于所有 DOM 原型对象。
    4. 由于 2020 年年中 WebIDL 规范的变化,浏览器正在向所有 DOM 原型对象添加 Symbol.toStringTag 属性。
    5. 所有内置对象的 [Symbol.toStringTag] 属性都是不可写的(writable)、不可枚举的(enumerable)但是可配置的(configurable)。

使用 toStringTag 自定义标签

javascript
class ValidatorClass {} 
Object.prototype.toString.call(new ValidatorClass()); // "[object Object]"
class ValidatorClass {
  get [Symbol.toStringTag]() {
    return "myValidator";
  }
}
Object.prototype.toString.call(new ValidatorClass()); // "[object myValidator]"
class ValidatorClass {} 
Object.prototype.toString.call(new ValidatorClass()); // "[object Object]"
class ValidatorClass {
  get [Symbol.toStringTag]() {
    return "myValidator";
  }
}
Object.prototype.toString.call(new ValidatorClass()); // "[object myValidator]"

toStringTag 适用于所有 DOM 原型对象

javascript
const test = document.createElement("button");
test.toString(); // [object HTMLButtonElement]
test[Symbol.toStringTag]; // HTMLButtonElement
const test = document.createElement("button");
test.toString(); // [object HTMLButtonElement]
test[Symbol.toStringTag]; // HTMLButtonElement

Object.prototype.toString.call()推荐

  • 描述
    1. 其本质上就是调用[Symbol.toStringTag]的属性。
    2. 一些值没有 [Symbol.toStringTag]属性,但是有toString()。这也是为什么他是判定最准确最全面的方法
javascript
console.log(Object.prototype.toString.call('1'))          // [object String]
console.log(Object.prototype.toString.call(1))            // [object Number]
console.log(Object.prototype.toString.call(null))         // [object Null]
console.log(Object.prototype.toString.call(undefined))    // [object Undefined]
console.log(Object.prototype.toString.call(true))         // [object Boolean]
console.log(Object.prototype.toString.call({}))           // [object Object]
console.log(Object.prototype.toString.call([]))           // [object Array]
console.log(Object.prototype.toString.call(function(){})) // [object Function]
console.log(Object.prototype.toString.call(new Map))      // [object Map]
console.log(Object.prototype.toString.call(new WeakSet))  // [object WeakSet]
console.log(Object.prototype.toString.call('1'))          // [object String]
console.log(Object.prototype.toString.call(1))            // [object Number]
console.log(Object.prototype.toString.call(null))         // [object Null]
console.log(Object.prototype.toString.call(undefined))    // [object Undefined]
console.log(Object.prototype.toString.call(true))         // [object Boolean]
console.log(Object.prototype.toString.call({}))           // [object Object]
console.log(Object.prototype.toString.call([]))           // [object Array]
console.log(Object.prototype.toString.call(function(){})) // [object Function]
console.log(Object.prototype.toString.call(new Map))      // [object Map]
console.log(Object.prototype.toString.call(new WeakSet))  // [object WeakSet]

封装成为直观的函数

javascript
function valueType(value) { 
    return Object.prototype.toString.call(value).slice(8, -1); 
}
valueType(1)  // 'Number'
valueType([]) // 'Array'
valueType({}) // 'Object'
function valueType(value) { 
    return Object.prototype.toString.call(value).slice(8, -1); 
}
valueType(1)  // 'Number'
valueType([]) // 'Array'
valueType({}) // 'Object'

强类推荐

适用于所有数据类型:几乎可以适用于所有可能的数据类型,包括基本数据类型和复杂数据类型。 不易受篡改,全面,可靠。