Future — 비동기 계산의 결과

Future — 비동기 계산의 결과

Future<V>비동기 계산의 결과를 나타내는 인터페이스예요. 계산 완료 여부 확인, 완료 대기, 결과 조회 메서드를 제공해요. 자바 동시성 프로그래밍에서 비동기 작업의 결과를 받아올 때 가장 기본적인 추상화예요.

출처: Java API Reference

본문

개념 이해하기

Future는 비동기 계산의 결과를 나타내요. 계산이 완료됐는지 확인하고, 완료를 기다리고, 결과를 조회하는 메서드를 제공해요. 결과는 계산이 완료됐을 때만 get으로 검색할 수 있으며, 준비될 때까지 필요하면 블로킹해요.

public interface Future<V>
  • 취소cancel 메서드로 수행돼요. 추가로 태스크가 정상 완료됐는지 또는 취소됐는지 판별하는 메서드가 있어요.
  • 계산이 완료되면 더 이상 취소할 수 없어요.
  • 취소 가능성(결과는 불필요)만을 위해 Future를 쓰고 싶다면 Future<?>를 선언하고 기본 태스크 결과로 null을 반환하면 돼요.

대표 구현으로 FutureTask, CompletableFuture, ForkJoinTask 등이 있어요.

활용 예

interface ArchiveSearcher { String search(String target); }
class App {
    ExecutorService executor = ...;
    ArchiveSearcher searcher = ...;
    void showSearch(String target) throws InterruptedException {
        Callable<String> task = () -> searcher.search(target);
        Future<String> future = executor.submit(task);
        displayOtherThings();              // do other things while searching
        try {
            displayText(future.get());     // use future
        } catch (ExecutionException ex) { cleanup(); return; }
    }
}

FutureTask 클래스는 Runnable도 구현하는 Future 구현이라 Executor로 실행될 수 있어요:

FutureTask<String> future = new FutureTask<>(task);
executor.execute(future);

메모리 일관성 효과: 비동기 계산이 수행한 동작은 다른 스레드의 대응하는 Future.get()에 뒤따르는 동작보다 happen-before 관계예요.

메서드

boolean cancel(boolean mayInterruptIfRunning) — 태스크 실행 취소를 시도해요. 이미 완료/취소됐거나 다른 이유로 취소할 수 없으면 효과가 없어요. 아직 시작되지 않았다면 실행되지 않아야 해요. 이미 시작됐다면 mayInterruptIfRunning이 스레드를 인터럽트해 중지할지 결정해요. 반환값이 태스크가 지금 취소됐는지를 반드시 나타내는 건 아니므로 isCancelled()를 쓰세요.

  • 반환: 취소할 수 없었으면 false(보통 이미 완료), 그 외 true

boolean isCancelled() — 정상 완료 전에 취소됐으면 true.

boolean isDone() — 완료됐으면 true. 정상 종료, 예외, 취소 중 어떤 경우든 true.

V get() throws InterruptedException, ExecutionException — 필요하면 계산이 완료될 때까지 기다린 뒤 결과를 조회해요.

  • CancellationException (취소), ExecutionException (계산이 예외를 던짐), InterruptedException

V get(long timeout, TimeUnit unit) throws InterruptedException, ExecutionException, TimeoutException — 최대 timeout까지 기다린 뒤 결과를 조회해요.

  • TimeoutException (대기 시간 초과) 등

default V resultNow() — 기다리지 않고 계산 결과를 반환해요. 호출자가 태스크가 이미 성공적으로 완료됐음을 아는 경우용. (JDK 19+)

  • IllegalStateException — 완료되지 않았거나 결과로 완료되지 않은 경우

default Throwable exceptionNow() — 기다리지 않고 태스크가 던진 예외를 반환해요. 호출자가 태스크가 예외로 완료됐음을 아는 경우용. (JDK 19+)

  • IllegalStateException — 완료되지 않았거나, 정상 완료됐거나, 취소된 경우

default Future.State state() — 계산 상태를 반환해요. Future.StateRUNNING, CANCELLED, FAILED, SUCCESS 중 하나예요. (JDK 19+)

더 알아보기 (Learn more)