본문 바로가기

TIL

[TIL] 스트림 공유

스트림 공유

  • 스트림 공유란 말 그대로 스트림을 공유한다는 의미입니다.

bind()의 스트림 공유

테스트

아래와 같이 코드를 구성 후 빌드를 해보겠습니다.

let tap = signInButton.rx.tap
            .map { "안녕 \(Int.random(in: 1...100))"}
        
        tap
            .bind(to: emailTextField.rx.text)
            .disposed(by: disposeBag)
        
        tap
            .bind(to: passwordTextField.rx.text)
            .disposed(by: disposeBag)
        
        tap
            .bind(to: nicknameTextField.rx.text)
            .disposed(by: disposeBag)

 

그러면 빌드 결과로 아래와 같이 서로 다른 결과가 도출되는 것을 알 수 있습니다.

 

이는 bind()는 기본적으로 스트림을 공유하고 있지 않다는 의미입니다.

또한, 이는 bind로 연결될 때마다 구독이 되어 불필요한 추가 연산이 발생할 수도 있다는 의미도 됩니다.

따라서 이를 해결하기 위해서 share() 메서드를 활용하여 스트림을 공유하도록 만들 수 있습니다.

bind() 스트림  공유하게 만들기

아래 코드와 같이 share() 매서드를 추가해 주면 bind()로 구독된 스트림을 모두 공유할 수 있습니다.

 let tap = signInButton.rx.tap
            .map { "안녕 \(Int.random(in: 1...100))"}
            .share() // bind()를 스트림이 공유되도록 추가
        
        tap
            .bind(to: emailTextField.rx.text)
            .disposed(by: disposeBag)
        
        tap
            .bind(to: passwordTextField.rx.text)
            .disposed(by: disposeBag)
        
        tap
            .bind(to: nicknameTextField.rx.text)
            .disposed(by: disposeBag)

 

위 코드를 시뮬레이터에서 빌드해보면 아래 사진과 같이 값이 서로 동일하게 출력되는 것을 알 수 있습니다.

 

서비스 규모가 커진다면? 대체 방법은?

서비스 규모가 좀 더 커질 경우, 일일이 스트림 처리가 어려울 수 있습니다. 따라서 이를 좀 더 효율적으로 사용하기 위해 bind() 대신 drive()를 사용할 수 있습니다.

 

bind() VS drive()

둘의 가장 큰 차이라고 한다면 스트림 공유가 내부적으로 구현되어 있느냐 아니냐의 차이일 것 같습니다.

위에서 앞서 설명드린바와 같이 bind() 메서드는 기본적으로 스트림 공유가 내부적으로 구현되어 있지 않습니다.

반면에 drive() 매서드는 내부적으로 .share() 매더스가 사용되어 스트림 공유가 가능합니다.

 

drive()

자 그러면 drive() 정말 스트름 공유가 되는지 테스트해 보겠습니다.

 

구현된 코드는 다음과 같습니다.

let tap = signInButton.rx.tap
            .map { "안녕 \(Int.random(in: 1...100))"}
            .asDriver(onErrorJustReturn: "")
        
        tap
            .drive(emailTextField.rx.text)
            .disposed(by: disposeBag)
        
        tap
            .drive(passwordTextField.rx.text)
            .disposed(by: disposeBag)
        
        tap
            .drive(nicknameTextField.rx.text)
            .disposed(by: disposeBag)

 

위 코드를 시뮬레이터에서 빌드해 보겠습니다.

 

빌드 결과 위 사진처럼 동일한 값을 방출한다는 것을 알 수 있습니다.

이는 drive()는 기본적으로 스트림이 공유되도록 구현되어 있다는 방증입니다.

 

지금까지 스트림 공유에 대해 간단히 알아보았습니다.

사실 스트림 공유라는 것은 네트워크 통신 처리와 밀접한 연관이 있어 이 부분은 추후에 한번 다뤄보도록 하겠습니다.

 

글 읽어주셔서 감사합니다.