4

为了真正理解 Javascript,而不是复制和粘贴 Javascript googler,我正在阅读 Eloquent Javascript 电子书,并且碰巧遇到了以下示例:

var chineseBox = {};
chineseBox.content = chineseBox;
show("content" in chineseBox);
show("content" in chineseBox.content);

令人惊讶的是,它们都输出true. 这本书本身声称,“运算符in可用于测试对象是否具有某种属性。它产生一个布尔值。”

我知道这show("content" in chineseBox);是在寻找content它确实拥有的属性,它的价值是chineseBox. 但是,为什么第二个show()工作?

为了进一步测试,我尝试了:

show("content" in chineseBox.content.content); //true

show("contents" in chineseBox.contents.content); //type error: undefined

show("contents" in chineseBox.content.contents); // invalid "in" operand

问题基本上是,变量 chineseBox{} 没有 content 属性......还是有?

4

2 回答 2

6

关键是这一行:

chineseBox.content = chineseBox;

这给出chineseBox了对自身的引用。所以:

show(chineseBox.content === chineseBox);

你应该看到也会输出true

因此'content'chineseBox以及chineseBox.contentchineseBox.content.content等等)中,因为它们都是同一个对象,它确实具有一个content属性。


让我们看看你的第二个和第三个例子。为什么一个给了一段TypeError时间另一个抱怨一个无效的in操作数?

在第二个示例中,您有:

show("contents" in chineseBox.contents.content);

为了让in操作员测试指定的属性(“content s ”)是否在指定的对象中,它首先必须评估该对象什么。你得到一个类型错误,因为chineseBox.contentsis undefined,所以你不能访问它的content属性,因为没有对象可以访问。

将此与第三个示例进行对比:

show("contents" in chineseBox.content.contents);

现在在这里in操作员至少比第二个示例中的操作更远。该chineseBox.content属性确实存在,访问它的content s属性会给你undefined. 所以那里没有错误。但是随后您会收到关键字本身的错误,in因为您无法检查属性是否在undefined.

换句话说,在第二个例子中,就像你在问“圣诞老人的房子里有精灵吗?” 圣诞老人不存在,所以没有“圣诞老人之家”这样的地方。在第三个示例中,您更像是在问“奥巴马棕色房子的椭圆形办公室在哪里?” 奥巴马存在,但他没有棕色的房子。

于 2013-08-30T21:41:13.033 回答
3
chineseBox.content = chineseBox;

由于自引用,请注意它chineseBoxchineseBox.content. 含义chineseBox, chineseBox.content, chineseBox.content.content, chineseBox.content.content.content, ad infinitum 都指同一个对象。

show("content" in chineseBox);
show("content" in chineseBox.content);
show("content" in chineseBox.content.content);
show("content" in chineseBox.content.content.content);
show("content" in chineseBox.content.content.content.content);
show("content" in chineseBox.content.content.content.content.content);

(在您的测试中,请注意“s”content之间的区别。)contents

于 2013-08-30T21:41:08.770 回答