Bug报告
🔎 搜索词
抱歉,难以表述。
🕗 版本与回归信息
- 此问题至少从版本3.3.3开始出现(在playground中最低的版本)
- 仅当
target
大于es5
时出现此问题
⏯ Playground链接
带有相关代码的playground链接
💻 代码
declare function create<T>(fn: (get: () => T) => T): T
// Error: Cannot find name '_self'.
const store = create((get: () => typeof _self) => {
const _self = {
id: 123
}
return _self
})
🙁 实际行为
如果tsconfig属性 target
大于 es5
,TS会报错:Cannot find name '_self'
,但 store
的类型推断是正确的。对于 es3
和 es5
,它可以正常工作。
🙂 预期行为
没有错误😄
我认为这可能与提升规则有关。因为es5没有 let
和 const
关键字,而 var
被认为是在函数内部可见的任何地方。但也许我是错的。
无论如何,如果它能正常工作就很好了,因为这样可以帮助编译器推断循环依赖的类型。这里是实际示例:
pmndrs/zustand#991 。
4条答案
按热度按时间vi4fp9gy1#
这真的不应该起作用。函数签名中的
typeof _self
指的是在函数外部定义的假设性_self
(与store
处于同一级别)-即使是提升的var
,这种作用域边界也存在。我不知道为什么在 ES3/5 下它不会产生错误,但据我所知,它应该会。kqlmhetl2#
我认为这是一个特性😄
由于它不影响运行时行为,可以实现,因为它真的很有用。但我猜它不会被实现。
gjmwrych3#
我们在这里有稍微不同的解析规则,以便考虑到参数默认值需要在ES5-中降级,而这些默认初始化发生在函数体中(这意味着它们可以看到参数名称,这意味着某些事情以一种重要的方式被遮蔽)。在这里统一出错似乎是正确的行为。
fnatzsnv4#
感谢您的解释,现在我明白了它的根源。