RxSwift의 Combining 연산자 정리 🚌 🚌 🚌 ~
연산자 목차
- startWith
- concat
- merge
- combineLatest
- withLatestFrom
- reduce
- scan
startWith
Observable 맨 앞에 element를 추가해서 방출해주는 연산자입니다.
let numbers = Observable.of(2,3,4)
numbers.startWith(1)
.subscribe(onNext: {
print($0)
}).disposed(by: disposeBag)
출력
// 1
// 2
// 3
// 4
concat
여러 Observable들을 순서대로 이어주는 연산자입니다.
let first = Observable.of(1,2)
let second = Observable.of(3,4)
let third = Observable.of(5,6)
Observable.concat([first,second,third])
.subscribe(onNext: {
print($0)
}).disposed(by: disposeBag)
출력
// 1
// 2
// 3
// 4
// 5
// 6
merge
concat과 다르게 마블 다이어그램에서 보는대로 각 observable에서 element가 방출되는 시점 순으로 합쳐주는 연산자입니다.
let left = PublishSubject<Int>()
let right = PublishSubject<Int>()
Observable.of(left.asObservable(),right.asObservable())
.merge()
.subscribe(onNext: {
print($0)
}).disposed(by: disposeBag)
left.onNext(1)
left.onNext(5)
right.onNext(4)
right.onNext(2)
left.onNext(102)
출력
// 1
// 5
// 4
// 2
// 102
combineLatest
observable들을 합쳐주는데 각 observable에서 마지막 시점에 방출했던 element를 합쳐줍니다.
마블다이어그램에서 1만 방출되었을 때는 합칠 수 없는 것을 알 수 있습니다. 합쳐서 방출할 수 있는 두 element가 생겼을 때, 1A, 2A, 2B...를 보면 알 수 있듯이 각 observable의 마지막에 방출한 element를 이용해 combine해줍니다.
let left = PublishSubject<Int>()
let right = PublishSubject<Int>()
Observable
.combineLatest(left, right, resultSelector: {
"\($0) \($1)"
})
.subscribe(onNext: {
print($0)
}).disposed(by: disposeBag)
left.onNext(1)
left.onNext(5)
right.onNext(4)
right.onNext(2)
left.onNext(102)
출력
// 5 4
// 5 2
// 102 2
withLatestFrom
combineLatest는 각 observable이 방출되는 모든 시점에 방출이 되었다면, withLatestFrom은 한가지 obsevable이 방출되는 시점에만 합쳐서 방출해줍니다.
이런 상황은 UI에서 검색할 때 많이 사용됩니다.
마블 다이어그램에서 첫번쨰 observable을 button, 두번째 observable을 textField라고 생각해보면,
textField를 칠때마다 검색해야하는 자동완성기능이 아니라면, 검색버튼을 눌러야 검색이 됩니다. 따라서 버튼을 누를 때 마지막 시점에 친 검색어를 넘겨줄 수 있습니다.
let button = PublishSubject<Void>()
let textField = PublishSubject<String>()
let observable = button.withLatestFrom(textField)
observable.subscribe(onNext: {
print($0)
}).disposed(by: disposeBag)
textField.onNext("Sw")
textField.onNext("Swif")
textField.onNext("Swift")
button.onNext(())
textField.onNext("Swift Good!")
button.onNext(())
출력
// Swift
// Swift Good!
reduce
일반 swift에도 있는 연산자입니다. 수학적 계산을 할 때 주로 사용합니다.
reduce((x,y) => x + y) 와 같이 쓰입니다.
let observable = Observable.of(1,2,3)
// 1
observable
.reduce(0, accumulator: +)
.subscribe(onNext: {
print($0)
}).disposed(by: disposeBag)
// 2
observable
.reduce(0, accumulator: {
summary, newValue in
return summary + newValue
})
.subscribe(onNext: {
print($0)
}).disposed(by: disposeBag)
출력
// 6
// 6
1번과 2번 방법 모두 같은 답입니다. 2번 방법이 더 눈에 들어오지만, 1번 방법과 같이 간단하게 사용할 수 있습니다.
scan
reduce와 정말 비슷하지만 한 가지 차이점은 매 시점마다 결과를 방출해줍니다. reduce는 연산의 마지막 결과만 보여줍니다.
아래 마블 다이어그램을 비교하면 그 차이점을 확실히 알 수 있습니다.
let observable = Observable.of(1,2,3)
observable
.scan(0, accumulator: +)
.subscribe(onNext: {
print($0)
}).disposed(by: disposeBag)
출력
// 1
// 3
// 6
출처
- https://reactivex.io/documentation/operators.html
- https://www.udemy.com/course/mastering-rxswift-in-ios/learn/lecture/13858552#overview
'iOS > RxSwift' 카테고리의 다른 글
[Operators] Transforming (0) | 2022.01.30 |
---|---|
[Operators] Filtering (0) | 2022.01.30 |
[Observables] 개념 (0) | 2021.05.14 |