Javascript 在ES6(ECMAScript 6)中访问[[NativeBrand]]/[Class]]

Javascript 在ES6(ECMAScript 6)中访问[[NativeBrand]]/[Class]],javascript,ecmascript-harmony,Javascript,Ecmascript Harmony,我正在阅读ES6的草稿,我注意到Object.prototype.toString部分中有这样一个注释: 历史上,此函数偶尔用于访问字符串 以前版本中使用的[[Class]]内部属性的值 本规范的各版本作为各种标准的标称类型标签 内置对象。toString的这个定义保留了 将其用作特定类型内置对象的可靠测试 但它并没有为其他应用程序提供可靠的类型测试机制 各种内置或程序定义的对象 通过阅读es讨论,在ES6草案中,[[Class]]似乎正在被[[NativeBrand]]]取代,以便他们可以将其

我正在阅读ES6的草稿,我注意到
Object.prototype.toString
部分中有这样一个注释:

历史上,此函数偶尔用于访问字符串 以前版本中使用的[[Class]]内部属性的值 本规范的各版本作为各种标准的标称类型标签 内置对象。toString的这个定义保留了 将其用作特定类型内置对象的可靠测试 但它并没有为其他应用程序提供可靠的类型测试机制 各种内置或程序定义的对象

通过阅读es讨论,在ES6草案中,
[[Class]]
似乎正在被
[[NativeBrand]]]
取代,以便他们可以将其指定为不可扩展(至少是这样)

出于好奇,我在FireFox和Chrome中运行了一个快速测试(启用了实验性JavaScript):

“WeakMap”
不是ES6草案中规定的
[[NativeBrand]]
之一。但是,此测试在两种浏览器上都返回了
“[object WeakMap]”

所以我很困惑。我有几个问题


1。Chrome和Firefox是否正常运行?

从阅读草稿的一种方式来看,听起来他们应该返回
[object object]
(所有这些都是非常新的,所以在这些浏览器的未来版本中看到这种变化我不会感到惊讶)。然而,我很难理解草案这一部分的意图,特别是因为有些地方有
“??”

任何一个关注es讨论的人是否有任何相关信息?或者任何能更好地理解草案语言的人


2。是否有
Object.prototype.toString
的替代方案?

从上面引用的注释来看,它听起来像是由于遗留原因而保留了
Object.prototype.toString
,好像现在应该使用新的东西来代替它。尤其是节点中读取
的部分,“它没有为其他类型的内置…对象提供可靠的类型测试机制”
。这是否意味着未来的内置程序不能用这种方法进行测试

让我们用一个具体的例子

如果我想确保从未知来源收到的对象是
字符串
对象(实际构造的
字符串
对象,而不是原始字符串),我可以执行以下操作:

if (Object.prototype.toString.apply(unknownObject) != '[object String]')
    throw new TypeError('String object expected.');
这让我知道
unknownObject
是否是
String
对象,无论它是在什么帧中构造的

我的问题是,这应该是我进入ES6的方法吗?还是有其他选择?类似于
Object.getNativeBrandOf


3。由于
[[NativeBrand]]
似乎不包括未来类型的对象,如何测试这些对象?

这样行吗

if (Object.prototype.toString.apply(unknownObject) != '[object Symbol]')
    throw new TypeError('Symbol expected.');
…假设
Symbol
是私有名称的最终名称

我应该用这个吗

if (Object.prototype.toString.apply(unknownObject) != '[object WeakMap]')
    throw new TypeError('WeakMap expected.');
。。。还是别的什么


我问这个问题的原因是,我目前正在编写代码,希望在可能的情况下,能够在一两年内尽可能轻松地过渡到ES6。如果有一个
Object.prototype.toString
的替代品,那么我可以将其填充进去并从那里继续。谢谢


更新 benvie的回答为我提供了一个正确的术语来搜索和理解我问题的答案

我发现了关于这个问题

以下是我的发现,对于其他提出同样问题的人:

1。Chrome和Firefox是否正常运行?

是的,下文解释了原因

2。是否有
Object.prototype.toString
的替代方案?

现在,在可能性的意义上,会有两个“替代品”,但在替代品的意义上,不会有

a.使用
@@toStringTag
符号。然而,我的理解是,
Object.prototype.toString
可能仍然应该使用
@@toString gTag
用于扩展可从
对象.prototype.toString
返回的结果。如果您有一个要添加自己的字符串标记的原型,可以使用
@@toStringTag
将该值设置为任何字符串
Object.prototype.toString
将返回此值,除非此值是ES5内置项之一,在这种情况下,字符串标记将以“~”开头

b.在用户定义的对象上使用专用符号。我读过一封电子邮件,宣传这是对用户定义的对象执行相同类型检查的最佳方式。然而,我不明白这是如何解决问题的,因为我不明白它是如何成为跨框架解决方案的,并且它不允许您检查ES6内置

因此,尽管有一些替代方案,但最好现在继续使用
Object.prototype.toString
,但有一点需要注意:

确保您有一个内置的ES5是可行的,例如
String
,但确保您有一个内置的ES6并不是万无一失的,因为它们可以被
欺骗。@@toStringTag
。我不确定这是为什么,我可能遗漏了一些东西,或者它可能会随着规范的发展而改变

3。由于
[[NativeBrand]]
似乎不包括未来类型的对象,如何测试这些对象?

如上所述,
Object.prototype.toString
仍然可以在ES6内置程序上使用,但它不是傻瓜式的,因为任何有权访问
@@toStringTag
符号的人都可以欺骗它。然而,也许不应该有一个傻瓜式的方法,因为
Object.prototype.toString(weakmap)='[Object-weakmap]'
并不意味着
weakma
if (Object.prototype.toString.apply(unknownObject) != '[object WeakMap]')
    throw new TypeError('WeakMap expected.');