在扩展中重新声明成员*有时*会隐藏原始成员。为什么?
Redeclaring members in an extension hides the original member *sometimes*. Why?
一个偶然的机会,我发现你可以在没有编译器抱怨的情况下这样做:
extension Date {
var timeIntervalSinceNow: TimeInterval {
return 1000
}
}
更奇怪的是,实际上 的计算结果为 1000:
Date().timeIntervalSinceNow
- 扩展名似乎隐藏了原来的成员。
所以我试着用我自己的 class:
class A {
var a: String {
return "A"
}
}
extension A {
var a: String {
return "a"
}
}
- 编译失败:"invalid redeclaration of 'a'".
我观察到这不会影响原始成员通过协议的使用,这是预期的隐藏行为:
extension Date {
var description: String {
return "XXXX"
}
}
let date: CustomStringConvertible = Date()
date.description // normal date
Date().description // "XXXX"
你能解释一下为什么会出现弹头现象吗?
之所以有效,是因为您在与原始变量声明不同的模块中声明此扩展。
跨模块可以重载变量名,但在我看来这是 Swift 的一个缺点,因为目前没有办法明确说明您想要的是哪个模块声明。
一个偶然的机会,我发现你可以在没有编译器抱怨的情况下这样做:
extension Date {
var timeIntervalSinceNow: TimeInterval {
return 1000
}
}
更奇怪的是,实际上 的计算结果为 1000:
Date().timeIntervalSinceNow
- 扩展名似乎隐藏了原来的成员。
所以我试着用我自己的 class:
class A {
var a: String {
return "A"
}
}
extension A {
var a: String {
return "a"
}
}
- 编译失败:"invalid redeclaration of 'a'".
我观察到这不会影响原始成员通过协议的使用,这是预期的隐藏行为:
extension Date {
var description: String {
return "XXXX"
}
}
let date: CustomStringConvertible = Date()
date.description // normal date
Date().description // "XXXX"
你能解释一下为什么会出现弹头现象吗?
之所以有效,是因为您在与原始变量声明不同的模块中声明此扩展。
跨模块可以重载变量名,但在我看来这是 Swift 的一个缺点,因为目前没有办法明确说明您想要的是哪个模块声明。