【问题标题】:Javascript: How can an object store a reference to another object's method, and call it "remotely"?Javascript:一个对象如何存储对另一个对象方法的引用,并将其称为“远程”?
【发布时间】:2011-08-30 16:26:17
【问题描述】:

所以,我得到了两个对象,a 和 b。现在,我想将 b 的方法之一传递给 a 对象,它应该存储它。让我们将该方法称为 b.met:

b.met=function(){
    alert(this.txt);
}

现在,我想从 a 调用 b.met。以下代码不起作用,因为 a.met 是 a 范围内 b.met 的克隆:

a.met=b.met;
a.met(); //Executes in the 'a' scope!

到目前为止,我发现的唯一方法是将方法的名称保存在字符串中并在 eval 语句中使用它:

a.toCall='b.met';
eval(a.toCall+'();');

既然每个人都说你应该避免使用 eval ......还有什么其他可能性?


编辑 - 在 cmets 中查看:所以我将代码更改为:

a:{
    processes:[],
    spawnProcess:function(type,id,closeFn){
    var closeFn=closeFn || 'function(){}';
    this.processes.push({type:type,id:id,closeFn:closeFn});
}

到:

a:{
    processes:[],
    spawnProcess:function(type,id,closeFn){
    var closeFn=function(){closeFn()} || 'function(){}';
    this.processes.push({type:type,id:id,closeFn:function(){closeFn()}});
}

执行以下代码时,出现递归过多的错误:

a.spawnProcess('','',b.met);
a.processes[0].closeFn();

【问题讨论】:

标签: javascript object methods reference eval


【解决方案1】:

最简单的解决方案:

a.met = function() { b.met(); };

或使用.bind(参见MDC),语义相同:

a.met = b.met.bind(b);

【讨论】:

    【解决方案2】:

    您存储对函数的引用。函数只是一个函数。它基于调用上下文得到this 的定义。

    因此,如果您存储 a.met = b.met 然后在该函数中调用 a.met() this === a

    阅读at the JavaScript garden about this

    您要做的是存储函数和调用它的上下文。

    这可以作为

    a.met = function() {
      b.met();
    }
    

    a.met = b.met.bind(b);

    .bind 需要 ES5。推荐的跨浏览器替代方案包括 _.bind$.proxy

    编辑

    你需要改变

    a.spawnProcess('','',b.met);

    a.spawnProcess('','', function() {
        b.met();
    });
    

    你可能也想要这个

    a: {
        processes: [],
        spawnProcess: function(type, id, closeFn) {
            this.processes.push({
                type: type,
                id: id,
                closeFn: closeFn || function() {}
            });
        }
    }
    

    【讨论】:

    • 我还没有尝试 .bind 方法,但是我尝试了你给我的其他解决方案,它对我想要做的事情不起作用......我把代码进入我的问题的底部,也许你可以看看?
    • @Alex btw 在 javascript 中模拟进程是个坏主意。使用网络工作者。 (JavaScript 是单线程的)
    【解决方案3】:

    如果你的函数很多并且有参数,你也可以这样做

    function B() {
        this.x = "I am b";
    }
    
    function A() {
        this.x = "I am A";
    }
    
    B.prototype.met = function() {
        alert(this.x);
    }
    
    A.prototype.met = B.prototype.met;
    

    您可以使用 B.prototype 所需的功能更新 A.prototype。

    【讨论】:

      猜你喜欢
      • 2020-05-24
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 2013-08-16
      • 1970-01-01
      • 1970-01-01
      • 2015-06-14
      • 1970-01-01
      相关资源
      最近更新 更多