Objective-C协议参数导入Swift自动缩短规则及规避方案咨询
问题1:参数名自动缩短规则的官方说明
你观察到的是Swift与Objective-C互操作时的API命名适配规则,该规则在Swift 3版本正式推出,目的是将不符合Swift语言命名规范的Objective-C API自动转换为更贴合Swift语法风格的签名:
- 当Objective-C的参数名包含of/with/by/from/on等通用介词,且介词后紧跟对应参数的类型名(或类型名片段、单复数变体)时,Swift会自动拆分参数名:介词保留为外部参数标签,类型名部分作为内部参数名。
- 你遇到的
lotOfPersons参数被自动拆分为外部标签lotOf、内部参数名lotOfPersons,就是这套规则的典型触发场景。
问题2:规避该问题的正规方案
无需修改原有命名,可通过以下三种正规方案解决:
方案1:在Swift实现侧对齐协议自动生成的签名
直接按照Xcode报错提示的协议要求签名实现即可,外部参数标签用自动生成的lotOf,内部参数名仍可保留lotOfPersons不影响业务逻辑使用:
class PhonebookSomeEventCallbackImpl: PhonebookSomeEventCallback { public func onEvent(_ outUserId: UUID, someNumValue: Int32, lotOf lotOfPersons: [PhonebookPerson]) { // 方法内部可直接使用lotOfPersons变量 } }
方案2:在Swift实现侧手动指定ObjC选择器
给Swift实现的方法添加@objc属性,手动绑定对应的Objective-C选择器,跳过自动命名转换校验:
class PhonebookSomeEventCallbackImpl: PhonebookSomeEventCallback { @objc(onEvent:someNumValue:lotOfPersons:) public func onEvent(_ outUserId: UUID, someNumValue: Int32, lotOfPersons: [PhonebookPerson]) { // 原有实现无需改动 } }
方案3:在Objective-C协议侧手动指定Swift签名
在Objective-C的协议方法定义处添加NS_SWIFT_NAME宏,手动指定该方法导入到Swift后的签名,禁用自动转换:
@protocol PhonebookSomeEventCallback - (void)onEvent:(nonnull NSUUID *)outUserId someNumValue:(int32_t)someNumValue lotOfPersons:(nonnull NSArray<PhonebookPerson *> *)lotOfPersons NS_SWIFT_NAME(onEvent(_:someNumValue:lotOfPersons:)); @end
修改后Swift侧直接用原来的方法实现即可正常编译。
内容的提问来源于stack exchange,提问作者Crazy Sage
相关产品推荐
相关产品推荐

