首页
学习
活动
专区
圈层
工具
发布
社区首页 >问答首页 >向前--在称呼“Super(.)”之前结束“`this`”(或:“WTF严肃的心灵扭曲的故事”)

向前--在称呼“Super(.)”之前结束“`this`”(或:“WTF严肃的心灵扭曲的故事”)
EN

Stack Overflow用户
提问于 2018-06-29 17:10:08
回答 1查看 29关注 0票数 0

经过一些修改之后,我最终在TypeScript中写了这个:

代码语言:javascript
复制
 class B extends A{
     constructor() {
         const c = new C(() => this.method());
         super(c);
         c.someMethod(this);
     }
 }

而且效果很好..。

让我们暂时搁置一下我为什么这么做(与我的问题无关)。

我的问题是:

  • 当我在调用super之前做一些事情时,它是如何编译的?
  • 如果还没有定义行const c = new C(() => this.method());闭包this,它是如何实现的呢?
  • 至少this不应该可用,或者我宁愿做const c = new C(this.method);,但它没有编译,抱怨this is not, yet, available

我在那儿漏掉了什么东西

EN

回答 1

Stack Overflow用户

回答已采纳

发布于 2018-06-29 18:27:42

是啊,我想我明白为什么这让你烦恼了。GitHub中的相关问题是微软/打字稿#3311。让我们看看我能否回答这些问题:

  • 当我在调用super之前做一些事情时,它是如何编译的?

显然是因为您没有成员初始化器。从相关问题:

如果没有成员初始化器,可以随时调用super . 如果您查看类成员初始化器是如何发出的,其原因就相当清楚了。成员初始化程序是在超级调用之后发出的(否则派生类初始化器不会正确地覆盖基类初始化);通过强制超级调用作为第一件事,编译器可以确保只有一个(正确)位置可以发出这些初始化器。 通过移除成员初始化器将超级调用移动到任何位置--这就明确了您期望每个类成员的初始化顺序是什么。

我认为语言设计人员认为在super调用之前可以做一些合法的事情(例如,做一些计算来确定将什么传递到super调用中),但是有一些事情是有问题的:成员初始化器(将JS作为对this的引用),以及对this的显式引用。

  • 至少这不应该是可用的,或者我宁愿做const c = new C(this.method);,但是它没有编译,抱怨this is not, yet, available

对,您不能在调用super之前引用裸super,因为this当时并不一定存在。

  • 如果还没有定义行const c = new C(() => this.method());闭包this,它怎么能关闭它呢?

对于被接受的闭包,我的猜测是,对this的引用不能被认为是在词汇上 super调用。这可能是编译器中的错误或设计限制,也可能不是。在您的例子中,如果C的构造函数没有真正调用函数,那么可能没有问题.闭包可能会将this.method的取消引用推迟到子类构造函数完成之后。但是由于C的构造函数可能调用该函数,所以代码可能是不安全的。

如果您强烈认为这应该会给出编译器警告,那么您可能希望在GitHub中提出一个问题并引用微软/打字稿#3311 (您不能评论这个问题,因为它已经锁定了)。

希望这能有所帮助。祝好运!

票数 2
EN
页面原文内容由Stack Overflow提供。腾讯云小微IT领域专用引擎提供翻译支持
原文链接:

https://stackoverflow.com/questions/51106550

复制
相关文章

相似问题

领券
问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档