계발자 블로그

[Coroutine] Flow 본문

Kotlin

[Coroutine] Flow

더구더구 2024. 4. 25. 23:08

Flow란?

코루틴 Flow는 Kotlin에서 비동기적인 연속적인 데이터 스트림을 처리하기 위한 라이브러리입니다.

이것은 비동기적으로 값을 생성하고 소비하는 데 사용되며,

연속적인 데이터 스트림을 표현할 수 있는 코루틴 유형입니다.

 

비동기적으로 작업을 처리하는 코루틴에서 Suspend 함수를 사용하면

작업이 모두 완료된 후에 단일 값만을 반환받을 수 있습니다.

 

하지만 중간중간 진행되는 코루틴 작업 중에 갱신되는 값까지 반환받을 수 있다면

로직 업데이트를 더 촘촘히 수행할 수 있습니다

Flow는 이런 요구를 충족하기 위해 만들어진 타입입니다.

 

 

Flow에서 데이터 스트림에 관여하는 주체는 Producer(생산자), Intermediary(중간 연산자), Consumer(소비자) 3개가 있습니다.

 

Producer가 비동기적으로 값을 생성하면

Intermediary에서는 값을 수정하거나 그대로 통과시키고

Consumer가 전달받은 값을 소모하게 됩니다.

 

먼저 생산자에서는 데이터를 발행하기 위하여 flow { } 코루틴 블록(빌더)를 통해 생성하고 emit 함수를 통해 방출합니다.

Suspend 키워드를 따로 붙여주지 않아도 블록 내부의 작업이 Coroutine에서 수행됩니다.

 

생산자에서 데이터를 발행하였으면 중간 연산자는 생성된 데이터를 수정할 수 있습니다.

대표적으로 map(데이터를 원하는 형태로 변환), filter(데이터 필터링), onEach(데이터를 변경 후 수행한 결과를 반환) 등이 있습니다.

 

생산자에서 데이터를 발행하고, 중간 연산자에서 데이터를 가공하였다면

소비자에서는 collect()를 이용하여 전달된 데이터를 소비할 수 있습니다.

 

Flow는 Cold stream입니다.

Cold stream은 누군가가 Consume 하기 전까지는 데이터를 발행하지 않습니다.

즉, 하나의 flow 객체는 여러 Consumer가 붙어서 데이터를 받아갈 수 있다는 것을 의미합니다.

 

Flow vs LiveData

둘 다 안드로이드에서 데이터 관리 및 UI 업데이트를 간편하게 처리할 수 있는 점에서 비슷해 보일수도 있지만 큰 차이가 있습니다.

 

LiveData

  • 생명주기를 가진 데이터 홀더
  • 메인 스레드에서 동작
  • 안드로이드와 밀접한 관계가 있음

Flow

  • Coroutine Scope 안에서 동작 
  • 안드로이드 lifecycle 감지 가능
  • 안드로이드 의존성 제거 가능

Flow는 Coroutine Scope 안에서 동작하기 때문에 ViewModel Scope나 Lifecycle Scope와 함께 사용하면 LiveData처럼

ViewModel 또는 Activity, Fragment의 생명주기에 맞춰서 동작을 실행하거나 정지할 수 있습니다.

 

Flow에는 LiveData와 비교하면 풍부한 연산자가 있어서 데이터를 필요에 따라 유연하게 변환할 수 있습니다.

Flow는 Kotlin 언어에 포함된 기능이기 때문에 LiveData와는 달리 Android 의존성으로부터 자유롭습니다.

 

LiveData는 생명주기를 가진 데이터 홀더로 UI와 연결하면 자동으로 화면을 업데이트 할 수 있다는 명확한 이점이 있습니다.

하지만 메인스레드에서 동작하기 때문에 워커스레드에서 작업을 처리해야 되는 데이터 레이어에서는 사용하기가 적절치 않고

안드로이드와 밀접하게 결합되어 있기 때문에 테스트가 까다로워진다는 한계가 있습니다.

 

Flow는 Coroutine Scope 안에서 동작하기 때문에 필요에 따라서 적당한 Thread를 골라서 사용할 수 있습니다.

안드로이드의 Lifecycle을 감지할 수 있고 안드로이드 의존성도 제거할 수 있습니다.

 

'Kotlin' 카테고리의 다른 글

[Kotlin] 추상 클래스 와 인터페이스  (0) 2023.07.16
[Kotlin] inline 함수, reified  (0) 2023.06.05
[Kotlin] Null 처리  (0) 2023.03.14
[Kotlin] 코틀린 Companion Object  (0) 2023.03.01
[Kotlin] Kotlin Property (코틀린 프로퍼티)  (0) 2023.03.01