Java Multithreading Tutorial With Example

CompletableFuture in Java with Example

Java 8 introduced many important features including lambdas, stream, etc.

CompletableFuture is also one of the most important features added in Java 8 which is useful in asynchronous programming.

If you are not aware of asynchronous programming, it is a form of parallel programming that allows a particular code block to run separately from the main thread and notifies the caller thread of its statuses like completion, failure or progress.

The main advantage of asynchronous programming is you can write non-blocking code that doesn’t block the main thread at all.

Therefore, your application will become more responsive and performance will increase.

Before we go further to create a few examples, let see what is the difference between Future and CompletableFuture?

Using CompletableFuture like a simple Future

CompletableFuture implements the Future , which means that it can be used to launch a task and retrieve a result later with the get () method.

However, it brings a lot more functionality. It also implements the new CompletionStage interface, which is also introduced in 1.8.

Let’s create a simple example.

In the above example, we have created an instance of CompletableFuture using no-arg constructor.

Hence, any client API who want to get the result from performAsync can call get() to get the result from the CompletableFuture.

In the above example get() method blocks until and unless the Future completes its task.

To avoid blocking the get() call forever, Let’s use completableFuture.complete();

completableFuture.complete () manually complete the Future.

To put it differently, all the client APIs who are waiting for the Future will get the result “Hello World”.

Multiple complete() call will be ignored.

The output of the above program would be:

CompletableFuture can throw Exceptions

CompletableFuture can also return/throw an exception using completeExceptionally method.

CompletableFuture can cancel() the execution

Suppose if you are not able to continue running performAsync and you want to cancel the asynchronous execution, then you can also cancel the execution using the cancel() method.

If we are blocked for result by calling get() method, then it will throw CancellationException.

Encapsulate a task using runAsync and supplyAsync

If you want to ignore the return value and simply want to execute code asynchronously then we can use runAsync orsupplyAsync.

runAsync or supplyAsync are static methods that allow us to create a CompletableFuture instance from the Runnable and Supplier functional types accordingly.

runAsync takes Runnable and returns CompletableFuture.

supplyAsync takes Supplier and returns CompletableFuture.