RxSwiftのPlaygroundを読んでみるシリーズ今回は流れてくる値をあれこれして別の流れにしてしまう操作についてです。
(Transforming_Operators)
Transforming Operators
流れてくるnextイベントの中身にいろいろな操作をして、
新たなObservableとして流す処理です。
map
nextの中身を操作して、新たなObservableとして流す。
Observable
.just("🍑")
.map { $0 + "🍐" }
.subscribe { print($0) }
.addDisposableTo(disposeBag)
結果
Next(🍑🍐)
Completed
flatMap, flatMapLatest
本流を流れてきた値をもとに、違う流れを作り、
本流と作った流れを同時に観察するObservableを返す。
本流を違う値が流れてきたときに、
それまで作った別の流れを引き続きsubscribeするのがflatMap、
それまで作った別の流れを破棄して新しく作った流れのみsubscribeするのがflatMapLatest。
flatMap
let disposeBag = DisposeBag()
struct Fruit {
var fruit: Variable<String>
}
let 🍑 = Fruit(fruit: Variable("🍑"))
let 🍎 = Fruit(fruit: Variable("🍎"))
let fruit川 = PublishSubject<Fruit>()
fruit川
.flatMap { $0.fruit.asObservable() }
.subscribe { print($0) }
.addDisposableTo(disposeBag)
fruit川
.onNext(🍑)
🍑.fruit.value = "🍊"
fruit川
.onNext(🍎)
🍑.fruit.value = "🍉" // 流れる
結果
Next(🍑)
Next(🍊)
Next(🍎)
Next(🍉)
flatMapLatest
let disposeBag = DisposeBag()
struct Fruit {
var fruit: Variable<String>
}
let 🍑 = Fruit(fruit: Variable("🍑"))
let 🍎 = Fruit(fruit: Variable("🍎"))
let fruit川 = PublishSubject<Fruit>()
fruit川
.flatMapLatest { $0.fruit.asObservable() }
.subscribe { print($0) }
.addDisposableTo(disposeBag)
fruit川
.onNext(🍑)
🍑.fruit.value = "🍊"
fruit川
.onNext(🍎)
🍑.fruit.value = "🍉" // 流れない
結果
Next(🍑)
Next(🍊)
Next(🍎)
scan
流れてくる値ごとに処理を行い、
処理した値を保持すると同時にその値を流す。
Observable
.of("🍑", "🍐", "🍑", "🍐", "🍑", "🍐")
.scan("🍎") { aggregateValue, newValue in // aggregateValueに処理の結果を保持する
aggregateValue + newValue
}
.subscribe { print($0) }
.addDisposableTo(disposeBag)
結果
Next(🍎🍑)
Next(🍎🍑🍐)
Next(🍎🍑🍐🍑)
Next(🍎🍑🍐🍑🍐)
Next(🍎🍑🍐🍑🍐🍑)
Next(🍎🍑🍐🍑🍐🍑🍐)
Completed
おわりに
flatMapはようやく感じが掴めてきました。
(文章にするのは尚難し。。)
次回はフィルターやある条件の元で値を流す処理についてです。