3

我想我在这里误解了一些东西。我有一个对象,其中包含我希望不可枚举的属性。我希望能够从对象的函数本身中为其分配值,但是当我这样做时,该属性变得可枚举。

例子:

function ObjectNode() {
}

Object.defineProperty(ObjectNode.prototype, "parent", {
    value:null
    // enumerable and configurable default to false
}

// Pass an ObjectNode instance and set this object node as its parent
ObjectNode.prototype.addChild = function(node) {
    node.parent = this;    // <-- node.parent is now enumerable
    ...more code...
};

实际发生的是,为 node.parent 分配一个值会创建一个名为 parent 的新“自己的”属性,它会覆盖原始属性。

有没有一种方法可以在不这样做的情况下在内部为不可枚举的属性赋值?还是我必须求助于在闭包中引用变量的 getter/setter 属性?

编辑:

GGG的回答值得称赞,因为正是他的建议让我得到了最终的答案。

我想要做的基本上是从“for(key in object)”语句中隐藏一个简单的属性。我能够这样做:

function ObjectNode() {
    Object.defineProperty(this, "parent", {
        value:null, 
        writable:true
    });
}

我一开始对此犹豫不决的一个原因是错误地理解我不希望每个实例都重新创建该属性。但是,呃,这就是实例属性!!!!

谢谢,GGG,帮助我重新调整我的大脑!

4

1 回答 1

2

您已经创建了原型属性的一个不可配置的属性,但它仍然可以被构造函数创建的对象的属性所遮蔽。

function ObjectNode() {
}

Object.defineProperty(ObjectNode.prototype, "parent", {
    value: null,
    configurable: false
})

ObjectNode.prototype.addChild = function (node) {
    node.parent = this;    // <-- node.parent is now enumerable
}

var mom = new ObjectNode();
var kid = new ObjectNode();

mom.addChild(kid);

console.log(kid.parent == mom);  // works, logs true

kid.parent = "foo";

console.log(kid.parent);  // works, logs "foo"

ObjectNode.prototype.parent = "foo"; 

console.log(ObjectNode.prototype.parent); // fails, logs null

要记住的是,对象的属性只是该对象的属性,而不是原型链中具有该对象的其他对象的属性。相反,请尝试在构造函数中创建新对象的不可配置属性:

function ObjectNode() {
    Object.defineProperty(this, "parent", {
        value: null,
        configurable: false
    })
}

当然,这将阻止您的addChild函数工作,因为该属性不再是可配置的。您可以考虑在该函数中定义属性,但在使用addChild.

总而言之,一般来说,你最好的选择是不要担心如果它不是绝对关键(而且我不确定它会在什么情况下)使事情变得不可配置。很长一段时间以来,如果没有该功能,世界就相处得很好。;)

于 2013-01-25T03:08:19.710 回答