如何将Fruit结构体映射为遵循FruitProtocol的对应结构体?
问题:可失败初始化器无法将Fruit转换为AppleFruit/PearFruit?
场景说明
我们定义了Fruit结构体,内部包含FruitType枚举、id属性,以及可选的Apple和Pear结构体实例。需要创建遵循FruitProtocol协议的AppleFruit和PearFruit结构体,它们需包含水果id以及对应类型的Apple或Pear数据。尝试实现的可失败初始化器无法正常工作,使用return和self=都无效,请问问题出在哪?
初始代码
struct Fruit { enum FruitType { case apple case pear case unknown } let id: String let type: FruitType let apple: Apple? let pear: Pear? } struct Apple { let something: String } struct Pear { let somethingElse: String }
尝试的初始化器代码
init?(from fruit: Fruit) { switch fruit.type { case .apple: guard let apple = fruit.apple else { return nil } Apple(...) case .pear: guard let pear = coreAsset.pear else { return nil } Pear(...) default: self = nil } }
问题分析与解决方案
核心问题点
- 未正确初始化目标结构体属性:代码里在
case .apple分支直接调用Apple(...),但AppleFruit应该包含id和apple两个属性,需要给当前结构体的这些属性赋值,而非仅创建Apple实例。 - 变量名笔误:
coreAsset.pear应改为fruit.pear,初始化器的参数是fruit。 - 结构体可失败初始化器用法错误:值类型(结构体)的可失败初始化器不能通过
self = nil触发失败,正确做法是使用return nil。 - 缺少协议与目标结构体定义:原代码未给出
FruitProtocol、AppleFruit和PearFruit的具体定义,这是实现转换的基础。
正确实现代码
先补充协议和目标结构体的定义,再实现正确的可失败初始化器:
// 定义通用协议 protocol FruitProtocol { var id: String { get } } // Apple专属结构体,遵循协议 struct AppleFruit: FruitProtocol { let id: String let apple: Apple // 可失败初始化器 init?(from fruit: Fruit) { guard fruit.type == .apple, let apple = fruit.apple else { return nil } self.id = fruit.id self.apple = apple } } // Pear专属结构体,遵循协议 struct PearFruit: FruitProtocol { let id: String let pear: Pear // 可失败初始化器 init?(from fruit: Fruit) { guard fruit.type == .pear, let pear = fruit.pear else { return nil } self.id = fruit.id self.pear = pear } } // 原有的Fruit、Apple、Pear定义保持不变 struct Fruit { enum FruitType { case apple case pear case unknown } let id: String let type: FruitType let apple: Apple? let pear: Pear? } struct Apple { let something: String } struct Pear { let somethingElse: String }
代码说明
- 每个专属结构体(
AppleFruit/PearFruit)都明确包含id和对应类型的数据属性,符合FruitProtocol要求。 - 可失败初始化器通过
guard语句同时校验水果类型和对应数据是否存在,任一条件不满足则返回nil。 - 初始化成功时,直接给当前结构体的
id和对应数据属性赋值,完成正确初始化。
内容的提问来源于stack exchange,提问作者André Gonçalves
相关产品推荐
相关产品推荐

