Javascript:使用原型描述符添加方法

时间:2010-05-30 20:00:48

标签: javascript

代码:

Sorter.prototype.init_bubblesort = function(){
  console.log(this.rect_array);
  this.end = this.rect_array.length;
  this.bubblesort();
}

Sorter.prototype.init = function(array,sort_type){
  this.rect_array = array;
  this.init_bubblesort();
}

上面的代码按预期工作,但是当我将init函数更改为:

Sorter.prototype.init = function(array,sort_type){
  var sort_types = {'bubblesort':this.init_bubblesort,
                'quicksort':this.init_quicksort,
                'liamsort':this.init_liamsort};
  this.rect_array = array;
  sort_types[sort_type]();
}

init_bubblesort函数导致错误,指出this.rect_array未定义。我试图了解为什么init_bubblesort不再能够访问其实例的变量。

3 个答案:

答案 0 :(得分:1)

您需要使用call来指定隐式参数(this)。

Sorter.prototype.init = function(array,sort_type){
  var sort_types = {'bubblesort':this.init_bubblesort,
                'quicksort':this.init_quicksort,
                'liamsort':this.init_liamsort};
  this.rect_array = array;
  sort_types[sort_type].call(this);
}

否则,没有与init_bubblesort方法关联的对象。

对于setTimeout,执行:;

var self = this;
setTimeout(function(){sort_types[sort_type].call(self);}, 1000);

在回调中,这将引用窗口,因此我们创建一个单独的变量(self),它将被关闭。

答案 1 :(得分:1)

您收到此错误的原因是函数内部引用的this被解析为该方法属性的对象。

在第一种情况下,这是Sorter对象,在第二种情况下,它是sort_types对象,当然,这些是不同的。

最简单的方法就是:

Sorter.prototype.init = function (array, sort_type) {
    var sort_types = {
        'bubblesort': "init_bubblesort",
        'quicksort': "init_quicksort",
        'liamsort': "init_liamsort"
    };
    this.rect_array = array;
    this[sort_types[sort_type]]();
}

作为替代方案,call可用于“更改”已执行方法的上下文。

要回答关于其他问题的评论,如果你需要推迟排序的执行,你可以这样做

Sorter.prototype.init = function (array, sort_type) {
    var sort_types = {
        'bubblesort': "init_bubblesort",
        'quicksort': "init_quicksort",
        'liamsort': "init_liamsort"
    };
    this.rect_array = array;
    var that = this;
    window.setTimeout(function(){
        that[sort_types[sort_type]]();
    }, 80);
}

在这种情况下,上下文保持不变。

答案 2 :(得分:1)

Matthew解决了你的问题,但看看你的代码,sort_types对象似乎有点多余给我,如果你只是用它来映射一个函数{带有前缀"foo"的{​​1}},你可以做一些简单的事情:

"init_foo"