일 | 월 | 화 | 수 | 목 | 금 | 토 |
---|---|---|---|---|---|---|
1 | 2 | 3 | 4 | |||
5 | 6 | 7 | 8 | 9 | 10 | 11 |
12 | 13 | 14 | 15 | 16 | 17 | 18 |
19 | 20 | 21 | 22 | 23 | 24 | 25 |
26 | 27 | 28 | 29 | 30 | 31 |
- PETERICA
- AWS EKS
- kotlin spring
- Elasticsearch
- Pinpoint
- kotlin querydsl
- 티스토리챌린지
- APM
- 기록으로 실력을 쌓자
- 코틀린 코루틴의 정석
- Spring
- Java
- minikube
- Linux
- AI
- IntelliJ
- Kubernetes
- 정보처리기사 실기
- aws
- 오블완
- MySQL
- kotlin
- 정보처리기사실기 기출문제
- CKA 기출문제
- kotlin coroutine
- mysql 튜닝
- CloudWatch
- CKA
- 공부
- 정보처리기사 실기 기출문제
- Today
- Total
피터의 개발이야기
[kotlin] Kotlin Coroutine의 비동기 처리 장점, RxKotlin의 Callback 지옥 본문
[kotlin] Kotlin Coroutine의 비동기 처리 장점, RxKotlin의 Callback 지옥
기록하는 백앤드개발자 2024. 5. 27. 10:10
ㅁ 들어가며
ㅇ 코틀린 코루틴의 개념을 정리하였다.
ㅇ 최근 트랜드인 비동기처리에 있어서 코틀린 코루틴의 차이점에 대해 알아보았다.
ㅁ Coroutine이란?
Coroutines은 Co + Routines 약자로, Co 는 Cooperation을 의미하고, Routines는 하나의 테스크를 의미한다. 풀어서 말하자면, 서로 협력하는 함수를 의미한다.
ㅁ 간결하고 읽기 쉬운 코드
ㅇ 코루틴을 사용하면 복잡한 비동기 작업을 마치 동기 코드처럼 작성할 수 있다.
ㅇ 이는 콜백 지옥을 피하고 코드의 가독성을 크게 향상시킨다.
ㅇ 아래는 코틀린의 가독성을 확인하기 위해 Callback 지옥, RxKotlin, coroutine을 비교해 보았다.
Callback 지옥
fun goWork(person: Person) {
val 잠든패카= person
wakeUp(잠든패카){ 비몽사몽한패카 ->
takeShower(비몽사몽한패카){ 깨끗한패카 ->
putonShirt(깨끗한패카){ 옷입은패카 ->
getOnBus(옷입은패카){ 버스를탄패카 ->
finish(버스를탄용준){ 출근한패카 ->
출근한패카.doWork()
} // finish end
} // getOnBus end
}// putonShirt end
}// takeShower end
} // wakeUp end
}
ㅇ Callback 함수의 기초는 람다 표현식이다.
ㄴ 람다 표현식은 메소드의 매개변수로 전달될 수도 있으며, 메소드의 결과값으로 반환될 수 있다.
ㄴ Java SE 8부터는 이러한 람다 표현식을 사용하여 자바에서도 함수형 프로그래밍을 할 수 있게 되었다.
ㄴ 람다 방식을 이용해 하나의 테스크가 마치면 callback 형태로 구현하였다.
ㅇ 콜백으로 비동기처리를 구현하면, 흔히 이야기 하는 콜백 지옥에 빠질 수 있다.
ㅇ 각 콜백 지옥의 복잡함을 해소하기 위해 "// ~~ end"로 표시하였다.
RxKotlin
fun goWork(person: Person) {
val 잠든패카= person
Observable
.just(person)
.observeOn(MAIN_Thread)
.subscribeOn(IO_Thread)
.flatMap{ 잠든패카 -> wakeUp(잠든패카)}
.flatMap{ 비몽사몽한패카 -> takeShower(비몽사몽한패카)}
.flatMap{ 깨끗한패카 -> putOnshirt(깨끗한패카)}
.flatMap{ 옷입은패카 -> getOnBus(옷입은패카)}
.flatMap{ 버스를탄패카 -> finish(버스를탄패카)}
.subscribet({ 출근한패카 ->
출근한패카.doWork()
}, {
실패했을때처리( )
}
}
ㅇ RxKotlin는 옵저버 패턴 구조로 되어 있다.
ㄴ 옵저번 패턴이란,
옵저버(관찰자)들이 관찰하고 있는 대상의 상태가 변경되면 각 관찰자들에게 알림을 받아 조치를 취하는 행동 패턴이다.
ㄴ Pub/Sub(발행/구독) 모델로 알려져 있다.
ㅇ 콜백 코드에 비해 flatMap을 기준으로 이전 테스크의 결과를 받아 후속 테스크가 수행되기 때문에 보기에 편하다.
ㅇ 하지만, Rx의 캡슐화되고 함수화로 내제화된 코드를 배워야하는 러닝커버가 있다.
ㄴ just, observerOn, subscribeOn의 개념뿐만 아니라 에러처리를 위한 개별 함수를 공부해야한다.
ㄴ 내제화된 코드에서 수행할 때에 내 생각과 의도치 않게 움직이는 경우가 많았다.
Kotlin + coroutine
suspend goCompany(person: Person){
val 잠든패카 = person
try {
val 비몽사몽한패카 = wakeUp(잠든패카)
val 깨끗한패카 = takeShower(비몽사몽한패카)
val 옷입은패카 = putonShtrt(깨끗한패카)
val 버스를탄패카 = getonBus(옷입은패카)
val 출근한패카 = finish(버스를탄패카)
출근한패카.doWork()
} catch (e: Exception){
실패했을때처리( )
}
ㅇ suspend를 사용하면 동기식 처럼 보이지만 비동기식으로 해석되어 실행되는 코드를 작성할 수 있다.
ㅇ 각 함수들의 작업은 언제 끝날지 모르지만 비동기 작업들의 순서는 정확히 지켜진다.
ㅇ 이게 무슨 말인가? 동기랑 비동기랑 무슨 차이가 있지 모를 수 있다.
ㅇ 여기서 suspend에 대해 더 이해가 필요하다.
ㅁ Coroutines의 비동기처리 이해를 위한 suspend와 block 비교
coroutine의 비동기처리는 thread를 suspend(유예하다)하지 block(차단하다)하지 않는다.
block
ㅇ block은 thread를 점유하게 되어 thread는 다른 처리를 진행할 수 없다.
ㅇ 태스크가 특정 조건(예: I/O 완료, 자원 사용 가능 등)을 기다리고 있을 때 발생한다.
ㅇ 조건이 만족되면 태스크는 다시 실행 상태로 전환된다.
ㅇ 블로킹 호출은 주로 동기 작업에서 사용된다.
fun main(){
println("Coroutine")
Thread.sleep(3000L) // 3초 동안 thread를 점유한다.
println("Hello")
}
결과:
Coroutine
Hello
suspend
ㅇ suspend 함수는 일시 중단될 수 있는 함수이다.
ㅇ 코루틴은 suspend 함수를 호출할 때, 현재 코루틴을 중단하고 다른 코루틴을 실행할 수 있다.
ㅇ suspend 함수는 비동기 작업을 수행할 때 유용하다. 예를 들어, 네트워크 요청이나 파일 I/O 작업을 수행할 때 사용된다.
ㅇ suspend 상태에서는 코루틴이 CPU를 점유하지 않으며, 다른 코루틴이 실행될 수 있다.
import kotlinx.coroutines.*
fun main(): Unit = runBlocking {
launch {
delay(3000L) // 3초간 처리를 중단. 스레드가 다음 스팩을 수행하여 Hello가 표시된다.
println("Coroutine")
}
println("Hello")
}
결과:
Hello
Coroutine
요약하자면,
suspend은 코루틴을 일시 중단하고, 다른 코루틴이 실행될 수 있게 한다. CPU를 점유하지 않으며, 비동기 작업에 적합하다.
block은 현재 스레드를 차단하고, 작업이 완료될 때까지 기다린다. CPU를 점유하며, 동기 작업에 적합하다.
ㅁ 함께 보면 좋은 사이트
쾌락코딩 - 코틀린 코루틴(coroutine) 개념 익히기
devkuma - Kotlin 코루틴(Coroutines)
'Programming > Kotlin' 카테고리의 다른 글
[kotlin] 코틀린 코루틴의 정석- CoroutineDispatcher (0) | 2024.05.29 |
---|---|
[kotlin] 코틀린 코루틴의 정석- 스레드 기반 작업의 한계와 코루틴의 등장 (0) | 2024.05.28 |
[kotlin] Springboot - Configuration properties (0) | 2024.05.25 |
[kotlin] Springboot - RestController 생성 및 WebMvcTest (0) | 2024.05.24 |
[kotlin] Springboot - JPA 의존성 주입 (2) | 2024.05.23 |