swift 协议扩展默认实现与 class 中的实际实现

swift protocol extension default implementation vs actual implementation in class

考虑以下代码:

protocol MyProtocol {
    static var name: String { get }
}

extension MyProtocol {
    static var name: String {
        return "unnamed"
    }
}

// does not specify its own name
class MyClass: MyProtocol {

}

//specifies its own name!
class MyClass2: MyProtocol {
    static var name: String {
        return "Specific name"
    }
}

let myClass = MyClass()
print("\(MyClass.name)")
//>>"unnamed"

let myClass2 = MyClass2()
print("\(MyClass2.name)")
//>>"Specific name"

swift 是否保证 classes(例如本例中的 MyClass2)具有协议 属性 的实际实现,在本例中 "name" , 这是从 class 使用的,而不是通过协议扩展的默认 "name" 实现之一?

拥有所需协议的默认实现 function/property 意味着您的符合类型将不必实现该 function/property,它们可以使用默认实现。

但是,如果符合类型确实实现了 function/property,那么编译器将始终调用更具体的实现,即符合 class 中的实现,而不是默认实现。

因此,即使您将 MyClass2 的实例存储在 MyProtocol 类型的变量中,您在访问 属性 时仍然会获得 MyClass2 实现变量。

let myClass2: MyProtocol = MyClass2()
type(of: myClass2).name // "Specific name"

在协议扩展中声明和定义的 non-required properties/functions 行为不同。如果您仅在协议扩展中声明了一个 property/function,那么即使您在符合规范的 class 中为其提供了不同的实现,您也无法从类型为协议类型而不是特定的符合类型。

protocol MyProtocol {
    static var name: String { get }
}

extension MyProtocol {
    static var name: String {
        return "unnamed"
    }

    // Optional protocol requirement
    static var nonRequired: String {
        return "nonRequired"
    }
}

// does not specify its own name
class MyClass: MyProtocol { }

//specifies its own name!
class MyClass2: MyProtocol {
    static var name: String {
        return "Specific name"
    }

    // Specific implementation
    static var nonRequired: String {
        return "Specific"
    }
}

let myClass = MyClass()
MyClass.name

let myClass2: MyProtocol = MyClass2()
type(of: myClass2).name // "Specific name"
type(of: myClass2).nonRequired // "nonRequired"
MyClass2.nonRequired // "Specific"