RxSwift

5. RxSwift Subject

Daesiker 2021. 10. 3. 16:36
반응형

1. Hot Observable vs Cold Observable

Observable은 Hot Observable과 Cold Observable로 크게 2가지 종류로 나뉜다.

Hot Observable

Hot Observable은 Observable을 생성하자마자 아이템들을 방출해준다.

따라서 Observable을 생성해도 Subscribe를 하지 않았다면 Item을 방출하기 때문에 아무런 결과가 안나온다.

Subscribe를 할 때 방출한 아이템부터 사용이 가능하기 때문에 Observable의 생성 시점과 Subscribe의 호출 시점이 중요하다.

마우스 이벤트, 키보드 이벤트, 시스템 이벤트에서 주로 사용된다.

Cold Observable

Cold Observable은 Hot Observable과 반대의 개념이다.

Hot Observable은 Observable을 생성하자마자 방출을 한다면 Cold Observable은 바로 방출하지 않고 Subscribe 이벤트가 오기까지 기다렸다가 Subscribe가 실행될 때 방출한다.

보통 일반적인 웹 요청이나 데이터베이스 쿼리를 사용할 때 사용한다.


2. Subject

App을 개발하다 보면 실시간으로 Observable에 값을 추가하고 Subscriber에게 이벤트나 값을 방출하는 것이 필요하다.

Subject는 Observable이자 Observer인 Type이다.

Subject는 Cold Observable을 Hot Observable로 변환이 가능하여 실시간으로 값을 추가하고 구독할 수 있다.

Subject는 PublishSubject, BehaviorSubject, ReplaySubject, AsyncSubject로 총 4개의 종류로 구성되어있다.

그 중 가장 많이 다루는 PublishSubject와 BehaviorSubject만 다룰 예정이다.

PublishSubject

PublishSubject는 기본값이 없는 Subject이다.

타입만 설정하고 이벤트를 방출하면 구독하기 전까지 가지고 있다가 구독하는 시점에 이벤트를 처리한다.

let disposeBag = DisposeBag()

        enum MyError: Error {
           case error
        }

        let subject = PublishSubject<String>()
        
        // 1번째 이벤트
        subject.onNext("Hello World")

        //1번째 구독
        subject.subscribe {
            print("1 : ", $0)
        }
        .disposed(by: disposeBag)
        
        //2번째 이벤트
        subject.onNext("안녕~")
        
        //2번째구독
        subject.subscribe {
            print("2 : ", $0)
        }
        .disposed(by: disposeBag)
        
        //3번째 이벤트
        subject.onNext("안녕하세요~")

        //subject.onCompleted()
        
        //4번째 이벤트
        subject.onError(MyError.error)
        
        //3번째 구독
        subject.subscribe {
            print("3 : ", $0)
        }
        .disposed(by: disposeBag)

        //1 :  next(안녕~)
        //1 :  next(안녕하세요~)
        //2 :  next(안녕하세요~)
        //1 :  error(error)
        //2 :  error(error)
        //3 :  error(error)

코드를 확인해보면 String타입의 PublishSubject인 subject를 선언하고 onNext() 함수를 통해 첫번째 이벤트인 "Hello World"를 만들어 주었다.

이벤트를 생성하기전에 구독하는 부분이 없기 때문에 이 값은 Subscribe를 통해 이벤트가 방출되지 않은 것을 알 수 있다.

1번째 Subscribe를 만들고 그 다음 2번째 이벤트인 "안녕"을 생성하였다. 이번에는 이벤트가 생성되기 전에 Subscribe가 있어서 출력이 된걸 알 수 있다.

3번째 이벤트인 "안녕하세요" 전에는 2개의 Subscribe가 있기 때문에 출력이 2번 되었다.

여기서 onError()나 onComplete() 메서드는 onNext()와 달리 Subscribe의 호출 시점과 상관 없이 모든 Subscribe에서 호출된다.

BehaviorSubject

PublishSubject와 달리 기본값이 존재한다.

또한 PublichSubject는 Subscribe()로 데이터를 방출할 때 이전의 데이터를 먼저 호출한다.

View를 호출할 때 기본값이 필요하다면 BehaviorSubject를 주로 사용한다.

let disposeBag = DisposeBag()

        enum MyError: Error {
           case error
        }
        //기본값 : 4
        let b = BehaviorSubject<Int>(value: 4)

        //이벤트 생성 : 10
        b.onNext(10)

        //이벤트 방출
        b.subscribe {
            print("BehaviorSubject >> ", $0)
        }
        .disposed(by: disposeBag)
        
        //이벤트 생성 : 100
        b.onNext(100)

        b.subscribe {
            print("BehaviorSubject222 >> ", $0)
        }
        .disposed(by: disposeBag)

        //b.onCompleted()
        b.onError(MyError.error)

        b.subscribe {
            print("BehaviorSubject333> ", $0)
        }
        .disposed(by: disposeBag)
        
        //BehaviorSubject >>  next(10)
        //BehaviorSubject >>  next(100)
        //BehaviorSubject222 >>  next(100)
        //BehaviorSubject >>  error(error)
        //BehaviorSubject222 >>  error(error)
        //BehaviorSubject333>  error(error)

1번째 Subscibe() 호출 시점을 보면 이전에는 10이라는 이벤트를 생성 했고 호출 후에는 100이벤트를 생성했다.

BehaviorSubject는 이전의 데이터를 호출하기 때문에 10과 100을 둘다 생성한 것을 알 수 있다.

2번째 Subscribe의 이번 데이터는 100이기 때문에 100을 호출하는 것을 알 수 있고

PublishSubject와 마찬가지로 onError()이나 onCompleted()는 Subscribe의 호출 시점과 상관없이 모든 Subscribe()를 통해 이벤트를 방출한 것을 알 수 있다.

반응형

'RxSwift' 카테고리의 다른 글

6. RxSwift Relay, Signal, Driver  (0) 2021.10.07
4. RxSwift Operator(2)  (0) 2021.09.30
3. RxSwift Oporator(1)  (0) 2021.09.07
2. RxSwift Observable이란?  (0) 2021.09.02
1. RxSwift란?  (0) 2021.08.23