转换为 Swift 3 重命名我自己的 Objective-C 方法

问题描述 投票:0回答:2

我将 swift 类与我的 Objective-C 代码混合在一起。使用 Swift 2.3,一切都很好并且按预期工作。

我最近转换为 Swift 3,由于 Swift 3 发生了所有重命名,它更新了多个 API 调用。我明白了。

但不好的是 Swift 3 似乎重命名了 my Objective-C 类中的一个方法。我拥有 Objective-C 类,并且我将该方法称为我想要的:

readDeliveryInfoItems
。但现在,转换为 Swift 3 后,我无法再在 Swift 类中调用
.readDeliveryInfoItems()
了。它告诉我它已重命名为
.readItems()

这毫无意义。并且 Objective-C 类仍然调用方法

readDeliveryInfoItems
,所以这里有一些幕后的事情发生。

我尝试将 Objective-C

readDeliveryInfoItems
方法重命名为
readDeliveryInfo
,构建(Swift 失败,因为它说
readInfo()
方法不存在,这很好),然后将该方法重命名回
readDeliveryInfoItems 
。然而,当我在此之后构建时,Swift 又回想起该方法被称为
readInfo()
。我希望这会欺骗 Xcode 刷新 Swift 桥接并将方法重命名回正确的名称
readDeliveryInfoItems()
,但事实并非如此。

我该如何解决这个问题?

更新以添加更多信息

我的 Objective-C 类的接口有这个函数声明:

- (nullable NSArray<XMPPDeliveryInfoItem *> *)readDeliveryInfoItems;

但是在该类的生成接口(请参阅下面 MartinR 的评论)中,函数声明是这样的:

open func readItems() -> [XMPPDeliveryInfoItem]?

该类中还有其他与

readDeliveryInfoItems
函数类似的函数,例如这个:

- (nullable NSArray<XMPPDeliveryInfoItem *> *)sentDeliveryInfoItems;

它们在生成的界面中看起来是正确的:

open func sentDeliveryInfoItems() -> [XMPPDeliveryInfoItem]?

所以我不明白为什么我只有一个函数会遇到这个问题。

objective-c swift swift3
2个回答
20
投票

翻译过程详细描述于

您的问题的相关部分是(强调我的):

从方法的基本名称中删除封闭类型的匹配项,以便 只要比赛开始于动词之后。例如,

extension UIViewController {
  func dismissViewControllerAnimated(flag: Bool, completion: (() -> Void)? = nil)
}

变成:

extension UIViewController {
  func dismissAnimated(flag: Bool, completion: (() -> Void)? = nil)
}

据我所知,这种修剪算法是在 StringExtras.cpp(并使用大量启发式方法), 和PartsOfSpeech.def 包含被视为动词的单词列表,例如

VERB(dismiss)
VERB(read)
VERB(send)

但是不是

VERB(sent)
。这就解释了为什么 – 稍微简化一下你的例子 –

@interface DeliveryInfo : NSObject
-(void)readDeliveryInfoItems;
-(void)sentDeliveryInfoItems;
@end

成为

open class DeliveryInfo : NSObject {
    open func readItems()
    open func sentDeliveryInfoItems()
}

类型名称在动词“read”之后被修剪,但在 非动词“发送”。 (你可以通过改变第二种方法来验证 命名为

sendDeliveryInfoItems
,然后映射到
sendItems()
。)

您可以使用

NS_SWIFT_NAME
覆盖映射:

-(void)readDeliveryInfoItems NS_SWIFT_NAME(readDeliveryInfoItems());

0
投票

粗略地说(我过于简单化了),如果方法名称上的后缀是与返回类型匹配的动词对象,则后缀将被删除。

一个更简单的例子是一个名为

readString
的方法,它返回一个 NSString。

你的方法符合这些参数(我告诉过你我过于简单化了,但你可以粗略地看到这是怎么回事),所以你得到了治疗。

就我个人而言,我认为这是一个错误,特别是因为在某些情况下,更改可能会导致名称冲突并导致调用该方法不可能(特别是当 Objective-C API 不属于您并且您无法更改它时)。例如,请参阅此问题:Swift 3(省略不必要的单词)导致两个函数具有相同的名称

© www.soinside.com 2019 - 2024. All rights reserved.