在Objective-C中,可以将符合协议的类指定为方法参数。例如,我的方法只允许符合UIViewController
的{{1}}:
UITableViewDataSource
我无法在Swift中找到一种方法(也许它还不可能)。您可以使用- (void)foo:(UIViewController<UITableViewDataSource> *)vc;
指定多个协议,但是如何要求该对象也属于特定类?
答案 0 :(得分:119)
您可以将foo
定义为通用函数,并使用类型约束来同时要求类和协议。
Swift 4
func foo<T: UIViewController & UITableViewDataSource>(vc: T) {
.....
}
Swift 3 (也适用于Swift 4)
func foo<T: UIViewController>(vc:T) where T:UITableViewDataSource {
....
}
Swift 2
func foo<T: UIViewController where T: UITableViewDataSource>(vc: T) {
// access UIViewController property
let view = vc.view
// call UITableViewDataSource method
let sections = vc.numberOfSectionsInTableView?(tableView)
}
答案 1 :(得分:24)
在Swift 4中,您可以使用新的&amp;签名:
let vc: UIViewController & UITableViewDataSource
答案 2 :(得分:16)
Swift书籍文档建议您使用带有where子句的类型约束:
func someFunction<C1: SomeClass where C1:SomeProtocol>(inParam: C1) {}
这保证“inParam”的类型为“SomeClass”,条件是它也遵守“SomeProtocol”。您甚至可以指定由逗号分隔的多个where子句:
func itemsMatch<C1: SomeProtocol, C2: SomeProtocol where C1.ItemType == C2.ItemType, C1.ItemType: SomeOtherProtocol>(foo: C1, bar: C2) -> Bool { return true }
答案 3 :(得分:4)
使用Swift 3,您可以执行以下操作:
func foo(_ dataSource: UITableViewDataSource) {
self.tableView.dataSource = dataSource
}
func foo(_ delegateAndDataSource: UITableViewDelegate & UITableViewDataSource) {
//Whatever
}
答案 4 :(得分:3)
答案 5 :(得分:0)
2015年9月的注释:这是斯威夫特早期的观察。
似乎不可能。 Apple也对他们的一些API有这种烦恼。以下是iOS 8中新引入的一个示例(从测试版5开始):
UIInputViewController
&#39; textDocumentProxy
财产:
在Objective-C中定义如下:
@property(nonatomic, readonly) NSObject<UITextDocumentProxy> *textDocumentProxy;
并在Swift中:
var textDocumentProxy: NSObject! { get }
答案 6 :(得分:0)
这种方式怎么样?:
<div style="display:flex;align-items:center;justify-content:center;" id="content">
<div>
<h1>I'd love to be centre aligned correctly.</h1>
</div>
</div>
答案 7 :(得分:0)
Swift 5 更新:
func yourFun<V: YourClass>(controller: V) where V: YourProtocol