2010-12-15 3 views
2

это замыкание работы:Могу ли я использовать y-combinator для получения ссылки на объект для этого закрытия?

var o = { 
    foo: 5 
}; 

o.handler = function(obj){ 
    return function() { 
     alert(obj.foo); 
    }; 
}(o); 

o.handler(); //alert('5') 

возможно определить обработчик рядный, возможно, что-то похожее на операцию у-комбинатора?

var o = { 
    foo: 5, 
    handler: function(obj){ 
     return function() { 
      alert(obj.foo); 
     }; 
    }(o); //pointer to o? ----------------------------- 
}; 

из академического любопытства, я не пытаюсь сделать это в рабочем коде

intro to the y-combinator

ответ

1

Нет, это невозможно, потому что в то время определения объекта буквального, переменная o не определена, а ссылка this во время определения не указывается o.

Если вы использовали временную ссылку на this во внешней функции и передали ее в закрытие, это сработало бы, но вы не смогли бы передать объект, чтобы получить свойство foo.

var o = { 
    foo: 5, 
    handler:function(){ 
     var self = this; 
     return function() { 
      alert(self.foo); 
     }; 
    } 
}; 

var h = o.handler(); 
h(); 
+0

Существует [всегда] `this` (только не правильный) – 2010-12-15 20:30:36

+1

@pst. Вы правы, в этом случае он ссылается на` window`. – 2010-12-15 20:32:22

0

Вы можете просто использовать this ключевое слово здесь:

var o = { 
    foo: 5, 
    handler: function() { 
     alert(this.foo); 
    } 
}; 

Это намного проще подход ... На самом деле, ваш подход даже не представляется возможным, так как o не определен, когда вы обратитесь к Это.

1

Это не возможно с объектным литеральным само по себе, как указывали другие. Однако процесс может быть завернут. Wether или нет «добавляет ничего» спорно. Это не то же самое, что Y-Combinator (возможно, половина из них?), Потому что он не пытается дать «рекурсивное имя» (насколько я могу судить, Y-Комбинаторы предполагают первоклассные функции и замыкания или способ имитировать такие).

function bindMany (dict, res) { 
    res = res || {} 
    for (var k in dict) { 
    if (dict.hasOwnProperty(k)) { 
     var v = dict[p] 
     res[k] = v instanceof Function ? v(res) : v 
    } 
    } 
    return res 
} 

var o = bindMany({ 
    foo: 5, 
    handler: function(obj){ 
    return function() { 
     alert(obj.foo) 
    } 
    } 
}) 

не проверенная, но показывает, что подход может быть приняты. Есть тонкие проблемы с этой и прототипной цепочкой на dict/res, если есть - упражнение для читателя.

Счастливое кодирование.

 Смежные вопросы

  • Нет связанных вопросов^_^