理想情况下,我想创建一个BaseViewController
类,它接受协议类型(委托),并有一个弱变量作为委托。像这样:
class BaseViewController<Delegate: AnyObject> {
weak var delegate: Delegate?
init(delegate: Delegate) {
self.delegate = delegate
super.init(...)
}
}
然后像这样从视图控制器继承:
protocol MyDelegate: AnyObject {
func funcA()
func funcB()
}
class SomeViewController: BaseViewController<MyDelegate> {
func doSomething() {
delegate?.funcA()
}
}
编译器会报错:
'BaseViewController'要求'MyDelegate'是一个类类型
我该如何解决这个问题来实现我所需要的?
提前感谢:)
这是因为在swift协议中不会向它们自己确认,所以你不能使用" myprotocol ";作为确认协议的具体类型"MyDelegate">
你可以做的是
protocol MyDelegate: AnyObject {
func funcA()
func funcB()
}
class BaseViewController<Delegate: MyDelegate> {
weak var delegate: Delegate?
init(delegate: Delegate) {
self.delegate = delegate
super.init(...)
//keeping OPs code as is
}
}
class SomeOtherDelegateClass: MyDelegate {
func funcA() {
//some code here
}
func funcB() {
//some code here
}
}
class SomeViewController: BaseViewController<SomeOtherDelegateClass> {
func doSomething() {
self.delegate?.funcA()
}
}
编辑1:
正如OP在评论中提到的那样,他试图在BaseViewController
中引入一个泛型属性,该属性将简单地保留对任何实例的弱引用,这些实例的类是由BaseViewController
的子类使用泛型决定/声明的,我将上述答案简化了一点
试试这个
protocol MyDelegate {
func funcA()
func funcB()
}
class BaseViewController<Delegate> where Delegate: AnyObject {
weak var delegate: Delegate?
init(delegate: Delegate) {
self.delegate = delegate
super.init(...)
//keeping OPs code as is
}
}
class SomeOtherDelegateClass: MyDelegate {
func funcA() {
//some code here
}
func funcB() {
//some code here
}
}
class SomeViewController: BaseViewController<SomeOtherDelegateClass> {
func doSomething() {
self.delegate?.funcA()
}
}
protocol MyDelegate2 {
func funcABCD()
}
class SomeOtherDelegateClass2: MyDelegate2 {
func funcABCD() {
//some code here
}
}
class SomeViewController2: BaseViewController<SomeOtherDelegateClass2> {
func doSomething() {
self.delegate?.funcABCD()
}
}
老实说,我真的看不出这个设计有什么好处!也许你需要重新审视代码结构,看看你是否能想出更好的代码结构:)你应该将你的委托设置为BaseViewController中通用类型T
的约束:
protocol MyDelegate: AnyObject {
func funcA()
func funcB()
}
class Delegated1: MyDelegate {
func funcA() { print("A1") }
func funcB() {}
}
class Delegated2: MyDelegate {
func funcA() { print("A2") }
func funcB() {}
}
class BaseViewController<T: MyDelegate>: UIViewController {
var delegate: T?
func doSomething() {
delegate?.funcA()
}
}
class SomeViewController1: BaseViewController<Delegated1> {}
class SomeViewController2: BaseViewController<Delegated2> {}
class TestClass {
let viewController1: SomeViewController1 = {
let viewController = SomeViewController1(nibName: nil, bundle: nil)
viewController.delegate = .init()
return viewController
}()
let viewController2: SomeViewController2 = {
let viewController = SomeViewController2(nibName: nil, bundle: nil)
viewController.delegate = .init()
return viewController
}()
// prints:
// A1
// A2
func myFunc() {
viewController1.doSomething()
viewController2.doSomething()
}
}