我可以在TypeScript lambda中访问其他吗?

时间:2012-12-18 13:27:54

标签: typescript

在打字稿中,我可以这样写:

$('#something').fadeOut(400, (): void => {
    this.invokeAnotherMethod();
});

编译时,TypeScript会自动确保这指向我的类而不是附带的函数:

var _this = this;
$('#something').fadeOut(400, function() {
    _this.invokeAnotherMethod();
});

然而,当我需要访问真实的而不是外部_this时呢?有语法可以参考吗?例如,我如何编写可编译为以下代码的代码:

var _this = this;
$('#something').fadeOut(400, function() {
    $(this).data('specialhide', true);
    _this.invokeAnotherMethod();
});

有可能吗?

3 个答案:

答案 0 :(得分:25)

您需要避免使用fat-arrow语法来执行此操作,因为您不希望保留this的词法范围。

var _me = this;
$('#something').fadeOut(400, function () {
    _me.invokeAnotherMethod();
    $(this).data('specialhide', true);
});

在此示例中,我使用_me而不是_this来避免与TypeScript生成的变量发生任何冲突。我也避免使用self,以避免与window.self混淆(感谢RockResolve)。

为什么!

ECMAScript 6规范具有箭头函数定义功能 - 这是TypeScript语言从中获取此功能的地方。当TypeScript将来定位ECMAScript 6时,它将保留() =>语法 - 因此它们无法在this的两个上下文中使用它而不会破坏未来的兼容性。

即使您可以想象他们如何更改TypeScript编译器以使ECMAScript 3或5中同时提供_thisthis,但它实际上会成为版本6中的问题。

答案 1 :(得分:2)

我想出了一条出路,正如我在以下答案中所述: How can I preserve lexical scope in TypeScript with a callback function

这是史蒂芬芬顿在答案中实现封闭的更好方法。我更喜欢它,因为方法签名文档的用法。

基本上,使用这样的方法:

fadeOutLambda(outerThis: YourClass): {(d: number, i: number): number}{
    return function(d: number, i: number){
        // Put your "fadeOut" logic here
        // refer to "this" to mean the dynamically scoped "this"
        // refer to "outerThis" to refer to the class instance
        alert(outerThis); // lexically scoped class instance
        alert(this); // dynamically scoped context caller
        return 999;
    }
}

答案 2 :(得分:0)

让我提供另一种不使用lambda的解决方案。 您可以将main作为属性附加(在此示例中称为 me )。

class MyClass
{
    constructor()
    {
        var button: HTMLElement = document.getElementById("buttonID");
        (button as any).me = this;
        button.onclick = this.buttonClick;
    }

    private buttonClick(e): boolean
    {
        var me: MyClass = (this as any).me;

        // Implementation using this (the button) and me (the class)

        return false;
    }
}