gpt4 book ai didi

ios - 具有关联类型要求和默认实现的 Swift 协议(protocol)

转载 作者:搜寻专家 更新时间:2023-10-31 22:06:39 24 4
gpt4 key购买 nike

长期以来,我一直在努力研究 Swift 协议(protocol)和关联类型。我再次从基础开始,真正了解出了什么问题,我遵循了这个 article Rob Napier 的 Swift Protocols with Associated Type Requirement 中的 TypeErasure,但我仍然没有运气。

找到下面的代码

// An Animal can eat
protocol Animal {
associatedtype Food
func feed(food: Food) -> Void
}

struct AnyAnimal<Food>: Animal {
private let _feed: (Food) -> Void
init<Base: Animal where Food == Base.Food>(_ base: Base) {
_feed = base.feed
}
func feed(food: Food) { _feed(food) }
}

// Kinds of Food
struct Grass {}

struct Cow: Animal {
func feed(food: Grass) { print("moo") }
}

struct Goat: Animal {
func feed(food: Grass) { print("bah") }
}

let grassEaters = [AnyAnimal(Cow()), AnyAnimal(Goat())]
for animal in grassEaters {
animal.feed(Grass())
}

现在我想在协议(protocol) Animal 中给出一个默认实现,如下所示

extension Animal {

func feed(food: Food) -> Void {
print("unknown")
}
}

当我从 struct Cow 中删除该函数时,我收到 Cow 不符合 Protocol Animal 的错误消息。

这是否意味着您不能同时使用类型删除和默认实现?有什么方法可以在执行 TypeErasure 的同时保留默认实现吗?

最佳答案

问题与类型删除无关,你会得到同样的结果如果删除 struct AnyAnimal<Food> 会出现错误消息定义。

如果删除 feed()方法来自 struct Cow然后编译器无法推断关联类型 Food .所以要么你在默认实现中使用具体类型:

extension Animal {
func feed(food: Grass) -> Void {
print("unknown")
}
}

struct Cow: Animal {
}

或者你定义一个类型别名 Food对于每种类型,使用默认实现:

extension Animal {
func feed(food: Food) -> Void {
print("unknown")
}
}

struct Cow: Animal {
typealias Food = Grass
}

也可以为 Food 定义默认类型在里面协议(protocol):

protocol Animal {
associatedtype Food = Grass
func feed(food: Food) -> Void
}


extension Animal {
func feed(food: Food) -> Void {
print("unknown")
}
}

struct Cow: Animal {
}

关于ios - 具有关联类型要求和默认实现的 Swift 协议(protocol),我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/36810270/

24 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com