Sobes.tech
Middle

Разкажете за концепцията на класа CompletableFuture.

sobes.tech AI

Отговор от AI

CompletableFuture е клас в Java 8+, реализиращ интерфейсите Future и CompletionStage. Той представлява асинхронно изчисление, което може да бъде завършено (или да даде грешка) в някакъв момент в бъдещето и върху резултата му могат да се изпълняват последващи действия декларативно, без блокиране на основния поток.

Основни възможности:

  • Асинхронно изпълнение: Позволява стартиране на задачи в отделен поток (или пул от потоци).
  • Композиция: Може да се обединяват няколко CompletableFuture, създавайки вериги от зависими действия.
  • Управление на изключения: Предоставя методи за обработка на грешки при асинхронни изчисления.
  • Неблокиращи операции: Резултатът или изключението се обработват, когато бъде завършено future, без явен get().

Ключови методи:

  • Създаване:
    • supplyAsync(Supplier<T> supplier): Стартира Supplier асинхронно и връща CompletableFuture с неговия резултат.
    • runAsync(Runnable runnable): Стартира Runnable асинхронно и връща CompletableFuture<Void>.
    • completedFuture(T value): Създава вече завършен CompletableFuture с дадена стойност.
  • Преобразуване:
    • thenApply(Function<T, U> fn): Прилага функция към резултата, когато future завърши.
    • thenAccept(Consumer<T> action): Изпълнява действие върху резултата, когато future завърши.
    • thenRun(Runnable action): Изпълнява действие, когато future завърши, игнорирайки резултата.
    • thenCompose(Function<T, CompletionStage<U>> fn): Позволява създаване на вериги, където резултатът на един future се използва за създаване на друг.
  • Комбиниране:
    • thenCombine(CompletionStage<U> other, BiFunction<T, U, V> fn): Обединява резултатите на двата future.
    • allOf(CompletableFuture<?>... cfs): Връща CompletableFuture<Void>, който се завършва, когато всички подадени futures се завършат.
    • anyOf(CompletableFuture<?>... cfs): Връща CompletableFuture<Object>, който се завършва, когато някой от подадените futures се завърши.
  • Обработка на изключения:
    • exceptionally(Function<Throwable, T> fn): Обработва изключение, връщайки алтернативна стойност.
    • handle(BiFunction<T, Throwable, U> fn): Обработва както резултата, така и изключението.

Пример:

// Стартиране на асинхронна задача
CompletableFuture<String> future = CompletableFuture.supplyAsync(() -> {
    try {
        Thread.sleep(1000); // Имитиране на дълга работа
    } catch (InterruptedException e) {
        throw new IllegalStateException(e);
    }
    return "Резултат от асинхронната операция";
});

// Изпълнение на действие след завършване на задачата (не блокиращо)
future.thenAccept(result -> {
    System.out.println("Получен резултат: " + result);
});

// Още едно действие, което зависи от първото
future.thenApply(String::toUpperCase)
      .thenAccept(upperCaseResult -> {
          System.out.println("Резултат в големи букви: " + upperCaseResult);
      });

// Изчакване на всички задачи (в реални приложения обикновено се избягва явно get/join)
// future.join();

CompletableFuture е мощен инструмент за писане на реактивен и неблокиращ код в Java, значително улеснявайки работата с асинхронност в сравнение с класическия интерфейс Future.