为什么Object.prototype.toString.call(foo)可以检测foo的类型?

Mia*_*ter 3 javascript

我知道我们可以在Javascript中检测变量的类型,如下所示:

Object.prototype.toString.call([]); // [object Array]
Object.prototype.toString.call({}); // [object Object]
Object.prototype.toString.call(''); // [object String]
Object.prototype.toString.call(new Date()); // [object Date]
Object.prototype.toString.call(1); // [object Number]
Object.prototype.toString.call(function () {}); // [object Function]
Object.prototype.toString.call(/test/i); // [object RegExp]
Object.prototype.toString.call(true); // [object Boolean]
Object.prototype.toString.call(null); // [object Null]
Object.prototype.toString.call(); // [object Undefined]
Run Code Online (Sandbox Code Playgroud)

但为什么?

这些值([object Array],[object String] ...)是如何返回的,以及它的作用Object.prototype.toString是什么?

the*_*eye 6

Object.prototype.toString基本上返回对象的[[Class]](实现细节)内部属性.引用ECMA Script 5.1规范中的部分,其中定义了该部分

  1. 如果this值为undefined,则返回"[object Undefined]".
  2. 如果this值为null,则返回"[object Null]".
  3. O是调用ToObject传递this值作为参数的结果.
  4. class[[Class]]O的内部属性的值.
  5. 返回字符串值是串联的三根弦的结果"[object ",class"]".

也,

[[Class]]对于每种内置对象,内部属性的值由此规范定义.所述的值[[Class]]的宿主对象的内部属性可以是除了之一的任何字符串值"Arguments","Array","Boolean","Date","Error","Function","JSON","Math","Number","Object","RegExp",和"String".[[Class]]内部属性的值在内部用于区分不同类型的对象.请注意,除了通过之外,本规范不提供程序访问该值的任何方法Object.prototype.toString.

因此,Object.prototype.toString是唯一可以访问该[[Class]]属性的函数.