gpt4 book ai didi

Swift 泛型和协议(protocol)不适用于 UIKit [可能的错误]

转载 作者:可可西里 更新时间:2023-11-01 01:39:39 24 4
gpt4 key购买 nike

TL;DR -> 滚动到底部

在尝试使用 Swift 面向协议(protocol)的编程中标记 Apple 时,我在尝试实现类之间的委托(delegate)模式时偶然发现了以下问题。

我将从这个例子开始:

protocol PhotoHandlerParent {}

class UIViewController {}

class MyViewController: UIViewController, PhotoHandlerParent {}

class PhotoHandler: NSObject, UIImagePickerControllerDelegate, UINavigationControllerDelegate {
weak var delegate: PhotoHandlerParent
}

到目前为止,还不错。 MyViewController 的实例会很高兴地分配为 PhotoHandler的委托(delegate)。但是说我不仅希望委托(delegate)对象符合 PhotoHandlerParent , 也是类 UIViewController .在此特定示例中,PhotoHandler可以提出和驳回 UIImagePickerController委托(delegate)其父 View Controller 。很像:

protocol PhotoHandlerParent {}

class UIViewController {}

class MyViewController: UIViewController, PhotoHandlerParent {}

class PhotoHandler: NSObject, UIImagePickerControllerDelegate, UINavigationControllerDelegate {
weak var delegate: UIViewController, PhotoHandlerParent
}

不幸的是,上面的代码不适用于 Swift。另一方面,Swift 确实有泛型,这在这种情况下可能会有所帮助。因此可以尝试:

protocol PhotoHandlerParent {}

class UIViewController {}

class MyViewController: UIViewController, PhotoHandlerParent {}

class PhotoHandler<Parent where Parent: UIViewController, Parent: PhotoHandlerParent>: NSObject, UIImagePickerControllerDelegate, UINavigationControllerDelegate {
weak var delegate: Parent
}

有趣的是,MyViewController 的一个实例会回去愉快地分配为PhotoHandler的委托(delegate)。没有编译错误,没有运行时错误。但是……

TL;DR:问题

运行 sample code对于这个问题,可以看到一个类的实例用泛型声明并设置为 UIImagePickerController它永远不会调用它的委托(delegate)。 UIImagePickerController 调用没有 泛型声明的对象实例.

我最好的假设是编译器不会提示,因为它可以验证 PhotoHandler符合 UIImagePickerControllerDelegate .但是,在运行时,PhotoHandler实例实际上是一个 PhotoHandler<MyViewController>例如,因此以某种方式干扰了 UIImagePickerController识别其委托(delegate)实际执行其协议(protocol)的能力。

还是我遗漏了什么?

干杯

最佳答案

从文档的角度来看,这是正确的行为,因为:

Method in a generic class cannot be represented in Objective-C


回复@Bell App Lab 评论:

打开this page并向下滚动到Lightweight Generics。请注意:

Aside from than these Foundation collection classes, Objective-C lightweight generics are ignored by Swift. Any other types using lightweight generics are imported into Swift as if they were unparameterized.

它基本上说泛型(ObjC -> Swift)只为基础集合类导入,其余的被忽略 - IOW 导入就像它们没有参数化一样。

也许我们可以期待 future 在这方面有所改进,但我对此表示怀疑。

关于Swift 泛型和协议(protocol)不适用于 UIKit [可能的错误],我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/31187540/

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