2017-10-28 135 views
0

我有(我認爲)應該是一個常見的場景。在一個數組的可觀察範圍內組合Observable's

我有一個可能有子視圖模型的ViewModel。 (父母和子女)都有一個Observable<Bool>來反映他們是否有關於其原始狀態的變化。

的代碼如下:

class ParentViewModel { 
    var children = Variable<[ChildViewModel]>([]) 

    var hasChanges: Observable<Bool> { 
     return Observable.combineLatest(children.value.map { $0.hasChanges }) 
      .map { (boolArray) in 
       boolArray.reduce(false) { $0 || $1 } 
     } 
    } 
} 

class ChildViewModel: CustomStringConvertible { 

    let title: Variable<String> 
    private let originalValue: String 

    var hasChanges: Observable<Bool> { 
     return title.asObservable() 
      .map { $0 != self.originalValue } 
    } 

    init(string: String) { 
     title = Variable<String>(string) 
     originalValue = string 
    } 

    var description: String { 
     return "\(type(of: self)) - \(title.value)" 
    } 

} 

這工作得很好,除了ParentViewModel有變化從children.value組合值,所以它不是一個真正的Observable(如果我的hasChanges綁定後添加ChildViewModel,它將不會被考慮在內)。

我要的是ParentViewModelhasChangestrue如果它的任何的孩子hasChanges是也是如此。

另一個失敗的嘗試,如下所示:

children.asObservable() 
    .flatMap { Observable.from($0) } 
    .flatMap { $0.hasChanges } 

這將返回有任何改變的最後一個孩子的最新值,但是如果兩個孩子有變化和一個返回到初始值,它使它返回false,這不是我所需要的。

回答

0

首先,.reduce()只有在上游完成時纔會發出。嘗試使用.scan()

另一種方法可能會被應用.merge()所有兒童觀測,並在此基礎之上做.combineLatest()