【发布时间】:2017-02-11 14:55:33
【问题描述】:
我有一个扩展来遍历视图控制器链(甚至通过容器视图,这非常方便)
public extension UIViewController // go up to a certain class
{
public func above<T>(_ : T.Type)->(T)
{
var p:UIResponder = self
repeat { p = p.next! } while !(p is T)
return p as! T
}
}
(除此之外,请注意,Swift3 需要 p.next 上的“!”:不幸的是,我不确定为什么。)
所以,假设你有一个视图控制器类“General”,你可以
self.above(General).clickedHamburgerMenuButton()
它会找到您上方的第一个“General”。一切都很好,但使用 Swift 3 你会收到这个警告......
缺少“.self”以引用“General”类型的元类型
好像想要这个
self.above(General.self).clickedHamburgerMenuButton()
1) 将General 更改为General.self 似乎......很危险......实际上它是否安全,并且 含义与 Swift 中的General 相同
2) 在扩展中
public func above<T>(_ : T.Type)->(T)
为什么这是一个元类型?我是否“做错了什么”并让它要求一个元类型而不仅仅是一个类型?
2) “元类型”到底是什么? (我真的无法在任何地方找到它的解释。)也就是说,除了“类本身”之外,“一般”可能意味着什么。 (不是实例,也不是静态实例,或其他任何东西......)
【问题讨论】:
-
能够为单参数函数省略
.self是 Swift 3 之前的一个错误,请参阅 swift class as parameter without .self。另请参阅this Q&A,了解为什么需要.self。至于关于元类型的信息,see this part of the documentation :)。在您的示例中,T.Type是元类型 -
感谢@Hamish,这是一个美丽且信息丰富的评论:)
-
顺便说一句,当然你的方法可以在没有强制解包的情况下编写,注意如果没有找到匹配的响应者,它会崩溃。
-
嗨@MartinR - 谢谢。如果我完全理解“强制展开”是什么,我将能够开始理解您的评论.. :-) thx