본문 바로가기
Android/안드로이드 프로그래밍 Next Step

[Next Step] 3. 스레드 풀 사용

by Diane_KIM 2023. 8. 12.

 

https://velog.io/@manx/ThreadThread-Pool-%EC%93%B0%EB%A0%88%EB%93%9C-%ED%92%80

스레드 만드는 방법

1) Thread 상속   2) Thread(Runnable) 생성자에 Runnable 전달  3) 스레드풀 사용

 

스레드풀

  • 대기 상태의 스레드를 유지 -> 스레드 종료/생성 오버헤드 줄임
  • 많은 개수의 비동기 작업 실행시 퍼포먼스 향상
  • 스레드 포함 리소스를 제한하고 관리

 

ThreadPoolExecutor

자바에서 스레드 풀은 ThreadPoolExecutor 클래스로 구현되어 있음 (AsyncTask도 내부적으로 사용)

public ThreadPoolExecutor(int corePoolSize, // 스레드 기본 개수
                          int maximumPoolSize, // 스레드 최대 개수
                          long keepAliveTime, // 태스크 종료할 때 제거하지 않고 대기하는 시간
                          TimeUnit unit, // keepAliveTime의 시간 단위 (TimeUnit.SECONDS)
                          BlockingQueue<Runnable> workQueue, // 요청된 작업들이 저장될 큐 : 작업 대기열 관리
                          RejectedExecutionHandler handler) // 작업요청 거부 시 처리할 핸들러
  • 스레드를 corePoolSize만큼만 유지하고, 추가로 요청이 들어오면 workQueue에 쌓는다
  • 시작시 작업중인 스레드가 corePoolSize보다 작으면 스레드를 새로 추가 (미리 생성 X)

workQueue 파라미터

  1. ArrayBlockingQueue : 큐 개수에 제한을 주고, 요청이 들어오면 큐에 쌓는다. 큐가 꽉찼으면 maximumPoolSize가 될 때까지 스레드들 추가해서 사용
  2. LinkedBlockingQueue : 큐 개수에 제한이 없다. (maximumPoolSize값 의미X)
  3. SynchronousQueue : 요청을 큐에 쌓지 않고, 준비된 스레드로 바로 처리 (큐 사용X)

handler 파라미터

ThreadPoolExecutor가 정지되거나 거부되는 방식을 정함

  • ThreadPoolExecutor.AbortPolicy : 기본값, 런타임 예외 발생
  • ThreadPoolExecutor.CallerRunsPolicy :  스레드 생성하지 않고, 태스크 호출하는 스레드에서 바로 실행
  • ThreadPoolExecutor.DiscardPolicy : 태스크 제거
  • ThreadPoolExecutor.DiscardOldestPolicy : workQueue에서 가장 오래된 태스크 제거 (가장 유용!)
    • ListView, ScrollView 등 화면에서 스크롤하면서 이동시 이미 지나가버린 화면보다 새로 보이는 화면이 상대적으로 더 중요하다
    • 이때 DiscardOldestPolicy를 사용하면 오래된 workQueue에서 제거하고 최신 태스크를 workQueue에 추가한다.

SheduledThreadPoolExecutor

화면 갱신을 하는 지연/반복 작업은 Handler를 쓰는게 적절하지만, 백그라운드에서 작업하는 경우에는 ScheduledThreadPoolExecutor를 고려하는게 좋다

 

Executors

Executors의 팩토리 메서드로 생성하면 용도에 맞는 메서드를 작성할 수 있다.

자주 쓰이는 팩토리 메서드

  • newFixedThreadPool(int nTreads) : nThreads 개수까지 스레드 생성
  • newCachedThreadPool() : 필요할때 스레드 생성. keepAliveTime이 60초로 길다는게 특징
  • newSingleThreadExecutor() : 단일 스레드를 사용해서 순차적으로 처리
  • newScheduledThreadPool(int corePoolSize) : corePoolSize개수의 ScheduledThreadPoolExecutor를 만듬