2016-08-18 180 views
1

有人可以解释为什么我在'this'变量的'setItem'函数中没有获得智能感知。我的理解应该是'_storageAdapter'属性的范围?TypeScript - 'this'默认为'any'

class TestClass { 
private testOne =() => { 
} 

_storageAdapter: { 
    toType: (obj: any) => string, 
    getItem: (key: string) => void, 
    setItem: (key: string, value: string) => void, 
} 
= { 
    toType: (obj: any) => { 
     return "hello"; 
    }, 
    getItem: (key: string) => { 
     this.testOne() // this is class scoped; 
    }, 
    setItem: function (key: string, value: any) { 
     this.toType(value); // this should be property scoped? but no intellisense? its just set to 'any' 
    } 
} 

}

回答

2

普通JS的功能不保存的this范围,例如:

class A { 
    obj = { 
     withoutScope: function() { 
      console.log(this); 
     }, 

     withScope:() => { 
      console.log(this); 
     } 
    } 
} 

编译成:

var A = (function() { 
    function A() { 
     var _this = this; 
     this.obj = { 
      withoutScope: function() { 
       console.log(this); 
      }, 
      withScope: function() { 
       console.log(_this); 
      } 
     }; 
    } 
    return A; 
}()); 

通知两者之间的差console.logwithoutScopethis whil e withScope具有_this(其在上面定义为var _this = this)。
这是打字稿编译器如何翻译arrow function,但是如果您使用ES6目标进行编译,那么它将保留它作为箭头功能而不使用_this = this技巧,但结果将是相同的。

如果你调用这些方法你:

let a = new A(); 
a.obj.withoutScope(); // Object {} 
a.obj.withScope(); // A { obj: Object } 

code in playground

在你的例子同样的情况,前两个功能是其保持this权利范围箭头的功能,但第三不。
您可以使用箭头功能也同样可以,或者你可以使用Function.prototype.bind功能:

setItem: function (key: string, value: any) { 
    this.toType(value); // this should be property scoped? but no intellisense? its just set to 'any' 
}.bind(this) 

但它可能只能帮你在运行时,因为我不知道你的智能感知会得到。

+0

谢谢。我想我的抱怨是,那么没有办法在构建或编译时检查错误。你可以在setItem中输入this.ANYTHING,它只会在运行时制动。另外,无论使用胖箭头还是常规函数,只能在_storageAdapter属性外调用_storageAdapter中的内部函数。 Bummer – dotsa

+0

您可以像使用其他两个箭头函数一样使用箭头函数,但为什么不只是将这些函数用作类方法,而是将它们放在该对象中? –

+0

是的。我可以将它提取到一个可选的接口和一个类。我只是想看看我能推多少TS,然后才能给我强烈的类型化对象和智能感知。 – dotsa

1

简体样本:

class TestClass { 
    private testOne =() => { 
    } 

    _storageAdapter: { 
     getItem: (key: string) => void, 
     setItem: (key: string, value: string) => void, 
    } 
    = { 
     getItem: (key: string) => { 
      this.testOne() // this is class scoped; 
     }, 
     setItem: function (key: string, value: any) { 
      this.somethingThatDoesNotExist(); // this should be property scoped? but no intellisense? its just set to 'any' 
     } 
    } 
} 

的原因是,function不捕获this,它真的会依赖于别人怎么称呼它的功能的用户。

一个箭头函数捕获this所以打字稿有更强的保证。

更多

一些标志,这样就不会陷入措手不及:noImplicitAnyhttps://basarat.gitbooks.io/typescript/content/docs/options/noImplicitAny.html

相关问题