[英]Swift Optional of Optional
對於我的項目,我必須創建一個代理AppDelegate,它將調用轉發到另一個AppDelegate。
UIApplicationDelegate有一個var window: UIWindow?
。 我的問題是,為什么我不能這樣做:
private lazy var realAppDelegate: UIApplicationDelegate = {
return AppDelegate()
}()
var window: UIWindow? {
get {
return realAppDelegate.window
}
set {
realAppDelegate.window = newValue
}
}
該代碼的問題是realAppDelegate.window
是一個UIWindow??
。
有人知道為什么嗎?
UIApplicationDelegate
協議的屬性window
聲明如下:
optional var window: UIWindow? { get set }
這意味着它是一個可選屬性 (在某種意義上說“實現UIApplicationDelegate
協議的類不被要求實現/具有此屬性 ”,就像在Objective-C中有@optional
那樣),並且該屬性是可選類型 Optional<UIWindow>
(或UIWindow?
)。
這就是為什么你最后有雙重可選類型的原因,因為那個window
屬性可能會或者可能不會在realDelegate中實現,如果是,它本身就是Optional<UIWindow>
/ UIWindow?
。
所以基本上你想要的是返回你的realAppDelegate
的window
屬性......只有當realAppDelegate
決定聲明該屬性本身時(它不需要這樣做,因為它是optional var
)。
realAppDelegate
沒有實現window
本身,你可能打算返回一個nil
UIWindow?
結果是。 realAppDelegate
確實實現了window
屬性,那么你需要按原樣返回它(這個實現返回一個實際的UIWindow
或者一個nil
)。 最簡單的方法是使用nil-coalescing運算符??
在斯威夫特。 a ?? b
a ?? b
表示“如果a是非nil,則返回a,但如果a為nil,則返回b”(如果a
是T?
類型,則整個表達式應返回T
類型的對象,其中in你的情況T
是UIWindow?
類型UIWindow?
)。
var window: UIWindow? {
get {
// If realAppDelegate.window (of type UIWindow??) is not implemented
// then return nil. Otherwise, return its value (of type UIWindow?)
return realAppDelegate.window ?? nil
// That code is equivalent (but more concise) to this kind of code:
// if let w = realAppDelegate.window { return w } else return nil
}
...
}
要實現setter,這是另一個問題。 根據這個SO答案 ,似乎不可能直接訪問協議的可選屬性的setter。 但你可以想象一個黑客來解決這個問題,通過聲明另一個使這個window
屬性要求成為必需的協議,然后嘗試在setter中強制轉換它:
@objc protocol UIApplicationDelegateWithWindow : UIApplicationDelegate {
var window: UIWindow? { get set }
}
class AppDelegateWrapper : UIApplicationDelegate {
...
var window: UIWindow? {
get {
return realAppDelegate.window ?? nil
}
set {
if let realAppDelWithWindow = realAppDelegate as? UIApplicationDelegateWithWindow
{
// Cast succeeded, so the 'window' property exists and is now accessible
realAppDelWithWindow.window = newValue
}
}
}
...
}
財產的聲明是
optional var window: UIWindow? { get set }
開頭的optional
意味着該屬性根本不必存在,那是第二個?
。
UIApplicationDelegate
是一個協議,實現它的類不必實現所有內容。
聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.