在es5类中链接的方法

时间:2017-11-10 16:17:15

标签: javascript oop prototypal-inheritance

CurrentUser = function (){}
CurrentUser.prototype = {
    record: undefined
}
CurrentUser.prototype.is = {
    get _parent() {return CurrentUser.prototype},

    get signedIn() {
        return !!this._parent.record
    }
}
User = new CurrentUser
User.record = {name:'Joe'}
User.is.signedIn //false

我在这里尝试做的是创建一个新用户,给他一些数据(记录)并根据它确定他是否已签名(如果他的记录有数据 - 他是签名的)。

但实际情况是User.is.signedIn getter正在访问CurrentUser.prototype而不是访问User实例。由于CurrentUser.prototype.recordundefined - User.is.signedIn会返回false

4 个答案:

答案 0 :(得分:2)

你似乎在寻找

CurrentUser = function (){}
CurrentUser.prototype = {
    record: undefined,
    get is() {
        var parent = this;
        return {
            get signedIn() {
                return !!parent.record;
            }
        };
    }
};
var user = new CurrentUser
user.record = {name:'Joe'}
user.is.signedIn // true

但我真的建议避免这种情况。在原型上放一个简单的isSignedIn()方法并完成它。

答案 1 :(得分:1)

我最终做到了这一点(在我找到解决方案之后看到了Bergi的回答)

CurrentUser.prototype = {
    record: undefined,
    get is() { return {
        _parent: this,
        get signedIn() {return !!this._parent.record}
    }}
}

User = new CurrentUser
User.record = {name:'Joe'}
User.is.signedIn //true

我们让is getter返回一个对象,该对象通过将CurrentUser.prototype分配给_parent来保存对_parent的引用。反过来,这个对象有自己的getter,在访问CurrentUser.prototype时可以访问is。瞧!
顺便说一句,如果你在CurrentUser.prototype getter中有许多其他方法\ getter,你可以将它重构为一个独立的对象,然后通过Object.defineProperty()将其添加到User.is.signedIn

PS
许多人反对将类方法链接起来,但没有人能说 为什么 我喜欢我的代码尽可能接近人类语言 - User.isSignedIn对我而言比is看起来更好;我还在is方法中添加了许多其他User相关的检查 - 因此它们不会使try-catch命名空间混乱。

答案 2 :(得分:0)

 class CurrentUser {
   constructor(){
    this.record = null; 
   }

   get isSignedIn(){
     return !!this.record;
   }

 }

const user = new CurrentUser;
console.log( user.isSignedIn );

user.record = {what:"ever"};
console.log(user.isSignedIn);

只需将getter放入原型本身,而不是放入子对象。

答案 3 :(得分:0)

不,没有办法。

解决方法1(使用call方法调整this绑定规则):



    function Foo() {
    this.x = 10;	
    }
    
    Foo.prototype.bar = {
    baz: function() {
    return this.x;	
    }	
    };
    
    var y = new Foo();
    
    console.log(y["bar"]["baz"].call(y));





解决方法2(我们在实例化时向Foo.prototype.bar添加对实例化对象的引用):



function Foo() {
Foo.prototype.bar._this = this;
this.x = 10;
}

Foo.prototype.bar = {
baz: function() {
return this._this.x;	
}	
};

var y = new Foo();

console.log(y["bar"]["baz"]());




请参阅this问题或this one