Android Thread(스레드)

강유리·2023년 4월 8일
0

Android 개념

목록 보기
1/3

안드로이드의 스레드는 다음과 같이 크게 두 가지로 나뉩니다.
- Main Thread (UI Thread)
- Background Thread

메인 스레드는 1개만 존재하고, 백 그라운드 스레드는 여러 개가 존재할 수 있습니다.

Thread

스레드는 Process(프로세스) 내에서 순차적으로 실행되는 실행 흐름의 최소 단위이다.

Main Thread (UI Thread)

안드로이드 시스템은 새로운 앱 실행 시 새로운 리눅스 프로세스를 시작한다.

  • 안드로이드는 리눅스 커널 기반입니다.

기본적으로 메인 activity를 비롯한 모든 component는 단일 process 및 Main Thread에서 실행된다.

Main Thread의 특징
1. 애플리케이션의 기본 실행 스레드
2. 대부분의 애플리케이션 코드가 실행
3. 화면의 UI를 그리는 담당
4. 안드로이드 UI 툴 킷 구성요소와 상호작용하고, UI Event를 사용자에게 응답하는 스레드
5. UI Event 및 작업에 대해 수 초 내 (일반적으로 5~10초 사이) 에 응답하지 않으면 안드로이드 시스템은 ANR (Application Not Responding) 팝업 창을 표시

5번의 특징을 보았을 때, 시간이 오래 걸리는 코드는 새로운 스레드를 생성해 처리해야 함을 알 수 있다.

Why?
지속적이고 유연한 사용자 환경을 제공하기 위해 존재한다. 사용자는 1초의 지연으로도 불편함을 느낄 수 있기 때문에 좋은 앱 서비스는 처리 자체에 지연이 존재해도, 사용자와 지속적으로 상호작용할 수 있어야 한다.

Background Thread

Background Thread 사용 이유
: 네트워크 작업, 파일의 업로드와 다운로드, 이미지 처리, 데이터 로딩 등의 작업의 모든 자세한 처리 시간 계산은 힘들다.
따라서 메모리 이외의 곳에서 데이터를 가져오는 작업을 Background Thread에서 수행한다.
★백그라운드 스레드로 메인 스레드에 집중될 수 있는 코드를 분산하여 더 효율적인 애플리케이션을 만들 수 있다.

Background Thread 생성방법

  1. Thread 객체를 통해 생성하는 경우
  2. Runnable Interface 구현
  3. 람다식으로 Runnable 익명객체 구현
  4. Kotlin에서 제공하는 thread() 구현

1. Thread 객체를 통해 생성하는 경우
Thread 클래스를 상속 받아서 스레드를 생성

//예제 1
class WorkerThread: Thread() { 
	override fun run() {
		var i = 0
		while (i < 10) {
			i += 1
			Log.i("WorkerThread", "$i")
		}
	}
}
override fun onCreate(savedInstanceState: Bundle?) {
	super.onCreate(savedInstanceState)
	setContentView(binding.root)

	var thread = WorkerThread() //Thread 객체 생성
	thread.start()  //start()로 thread 실행
}

2. Runnable Interface 구현
Runnable Interface 구현으로 Thread 생성

Runnable Interface란?
: 다중 상속을 허용하지 않는 코틀린 언어의 특성상 상속 관계에 있는 클래스도 구현할 수 있도록 지원하는 모델

//예제 2
class WorkerRunnable: Runnable {
	override fun run() {
		var i = 0
		while (i < 10) {
			i += 1
			Log.i("WorkerThread", "$i")
		}
	}
}
override fun onCreate(savedInstanceState: Bundle?) {
	super.onCreate(savedInstanceState)
	setContentView(binding.root)

	var thread = Thread(WorkerRunnable) // 차이점
	thread.start()
}


3. 람다식으로 Runnable 익명객체 구현

인터페이스 내부에 메서드가 하나만 있는 경우는 람다식으로 변환이 가능
Runnable 인터페이스를 이용한 스레드는 람다식으로 변환이 가능

//예제 3
Thread {
	var i = 0
	while (i < 10) {
		i += 1
		Log.i("WorkerThread", "$i")
	}
}.start() //람다식

람다식(Lambda Expression)?
: 이름이 없이도 함수의 역할을 수행하는 익명 함수

4. Kotlin에서 제공하는 thread() 구현
thread() 안에 파라미터로 start = true를 전달하면 thread() 안의 코드 블록이 실행된다.

//예제 4
thread(start = true) {
	var i = 0
	while (i < 10) {
		i += 1
		Log.i("WorkerThread", "$i")
	}
}

Background Thread 주의사항

★백그라운드 스레드는 UI구성요소에 접근하면 안된다.

//예제 5
override fun onCreate(savedInstanceState: Bundle?) {
	super.onCreate(savedInstanceState)
	setContentView(binding.root)
	
	Thread {
		var i = 0
		while (i < 10) {
			binding.textView.text = "$i"  //UI 요소에 접근 
			i += 1
			Log.i("WorkerThread", "$i")
		}
	}.start()
}

예제 5의 코드와 같이 UI에 접근 시
"Only the original thread that create a view hierarchy can touch its view" 라는 error message가 뜬다.

profile
리유

0개의 댓글