2016-07-18 170 views
0

我即將編寫一個帶有默認擴展名的小型協議,可以決定是否設置所有參數。 (Swift 2.2)如何判斷孩子是否爲零

我的想法是使用鏡像類型並獲取給定類型的所有子元素,而不是遍歷它們。就像這樣:

var isComplete: Bool { 
    get { 
     return Mirror(reflecting: self).children.reduce(true) { return $0 && $1.value != nil } // <- Error, because value is not Optional 
    } 
} 

的問題是在孩子的類型,這是:

typealias Child = (label: String?, value: Any) 

所以我不能只檢查是否是零,因爲它是不可選的。如果使用print($1.value)它會打印出零,所以必須有一些指針魔術。

任何想法如何檢查內存地址。或者一些更簡單的方法來實現這個功能

+0

這個怎麼樣(1)?它可能會給你一些關於指針的信息,但肯定會是一件怪事。 (1)http://swiftdoc.org/v2.2/func/unsafeAddressOf/#func-unsafeaddressof_-anyobject – Mrwerdo

+0

當然,但不幸的是,這需要它的參數是AnyObject,我只有任何,所以它不會工作的事件用 'if let someObject = $ 1.value as? AnyObject {somePointer = unsafeAddressOf(someObject) }' 導致大多數屬性都是值類型。 – gujci

回答

0

好,我知道從https://stackoverflow.com/a/34637228/3308103

解決問題的關鍵是,我們不得不再次鏡像價值,並得到它的孩子,這些算不算是1,如果它有一個值。

因此,解決辦法是哈克,但如果有人需要它...

public protocol OptionalValueObservable { 
    var isComplete: Bool {get} 
    var hasAnyProperty: Bool {get} 
} 

public extension OptionalValueObservable { 
    var isComplete: Bool { 
     get { 
      return Mirror(reflecting: self).children.reduce(true) { acc, val in 
       let subMirror = Mirror(reflecting: val.value) 
       return acc && (subMirror.displayStyle == .Optional ? subMirror.children.count > 0 : true) 
      } 
     } 
    } 

    var hasAnyProperty: Bool { 
     get { 
      return Mirror(reflecting: self).children.reduce(false) { acc, val in 
       let subMirror = Mirror(reflecting: val.value) 
       return acc || (subMirror.displayStyle == .Optional ? subMirror.children.count > 0 : true) 
      } 
     } 
    } 
}