Java Callable Future Example

One of the benefits of the Java executor framework is that we can run concurrent tasks that may return a single result after processing the tasks. The Java Concurrency API achieves this with the following two interfaces Callable and Future.

1. Java Callable and Future interfaces

1.1. Callable

Callable interface has the call() method. In this method, we have to implement the logic of a task. The Callable interface is a parameterized interface, meaning we have to indicate the type of data the call() method will return.

2.2. Future

Future interface has methods to obtain the result generated by a Callable object and to manage its state.

2. Java Callable Future Example

In this example, We are creating a FactorialCalculator which is of type Callable. It means we will override it’s call() method and after calculation, we will return the result from call() method. This result later can be retrieved from Future reference held by main program.

public class FactorialCalculator implements Callable<Integer>
{

	private Integer number;

	public FactorialCalculator(Integer number) {
		this.number = number;
	}

	@Override
	public Integer call() throws Exception {
		int result = 1;
		if ((number == 0) || (number == 1)) {
			result = 1;
		} else {
			for (int i = 2; i <= number; i++) {
				result *= i;
				TimeUnit.MILLISECONDS.sleep(20);
			}
		}
		System.out.println("Result for number - " + number + " -> " + result);
		return result;
	}
}

Now let’s test the above factorial calculator using two threads and 4 numbers.

package com.howtodoinjava.demo.multithreading;

import java.util.ArrayList;
import java.util.List;
import java.util.Random;
import java.util.concurrent.Callable;
import java.util.concurrent.ExecutionException;
import java.util.concurrent.Executors;
import java.util.concurrent.Future;
import java.util.concurrent.ThreadPoolExecutor;
import java.util.concurrent.TimeUnit;

public class CallableExample 
{
	  public static void main(String[] args) 
	  {
		  ThreadPoolExecutor executor = (ThreadPoolExecutor) Executors.newFixedThreadPool(2);
		  
		  List<Future<Integer>> resultList = new ArrayList<>();
		  
		  Random random = new Random();
		  
		  for (int i=0; i<4; i++)
		  {
		      Integer number = random.nextInt(10);
		      FactorialCalculator calculator  = new FactorialCalculator(number);
		      Future<Integer> result = executor.submit(calculator);
		      resultList.add(result);
		  }
		  
		  for(Future<Integer> future : resultList)
		  {
	            try 
	            {
	                System.out.println("Future result is - " + " - " + future.get() + "; And Task done is " + future.isDone());
	            } 
	            catch (InterruptedException | ExecutionException e) 
	            {
	                e.printStackTrace();
	            }
	        }
	        //shut down the executor service now
	        executor.shutdown();
	  }
}

Program output.

Result for number - 4 -> 24
Result for number - 6 -> 720
Future result is -  - 720; And Task done is true
Future result is -  - 24; And Task done is true
Result for number - 2 -> 2
Result for number - 6 -> 720
Future result is -  - 720; And Task done is true
Future result is -  - 2; And Task done is true

Here we sent a Callable object to be executed in an executor using the submit() method. This method receives a Callable object as a parameter and returns a Future object that we can use with two main objectives –

  1. We can control the status of the task – we can cancel the task and check if it has finished. For this purpose, we have used the isDone() method to check if the tasks had finished.
  2. We can get the result returned by the call() method. For this purpose, we have used the get() method. This method waits until the Callable object has finished the execution of the call() method and has returned its result.

    If the thread is interrupted while the get() method is waiting for the result, it throws an InterruptedException exception. If the call() method throws an exception, this method throws an ExecutionException exception.

The Future interface provides another version of the get() method i.e. get(longtimeout,TimeUnitunit). This version of the get method, if the result of the task isn’t available, waits for it for the specified time. If the specified period of time passes and the result isn’t yet available, the method returns a null value.

Happy Learning !!

Was this post helpful?

Join 7000+ Fellow Programmers

Subscribe to get new post notifications, industry updates, best practices, and much more. Directly into your inbox, for free.

14 thoughts on “Java Callable Future Example”

  1. I just saw in Java 8 ,The Future‘s method get(longtimeout,TimeUnitunit)shouldt hrows TimeoutException if the wait timed out, not return null .

    Reply
    • Yep, you are right it should throw the TimeoutException and not null. Here is the implementation.

          public V get(long timeout, TimeUnit unit)
              throws InterruptedException, ExecutionException, TimeoutException {
              if (unit == null)
                  throw new NullPointerException();
              int s = state;
              if (s <= COMPLETING &&
                  (s = awaitDone(true, unit.toNanos(timeout))) <= COMPLETING)
                  throw new TimeoutException();
              return report(s);
          }
      
      Reply
  2. Thank you for the great article.
    But, how to run task periodically (every n seconds) and retrieve some result, which is needed in further processing? Is it wise to use in indefinite while(true) loop, the method schedule (Callable task, long delay, TimeUnit timeunit)?

    Reply
  3. Here is the code

    class TestTRejectedExecutionHandler implements RejectedExecutionHandler {
    @Override
    public void rejectedExecution(Runnable r, ThreadPoolExecutor executor) {
    try {
    System.out.println(“Rejected Execution Handler For Thread ” + Thread.currentThread().getName());
    Thread.sleep(1000);
    } catch (Exception e2) {
    // TODO: handle exception
    }
    executor.execute(r);
    }
    }

    class TestTTask implements Callable {
    @Override
    public String call() {
    try {
    Thread.sleep(1000);
    } catch (Exception e) {
    // TODO: handle exception
    }
    return Thread.currentThread().getName();
    }
    }

    public class TestT {
    public static void main(String[] args) throws InterruptedException, ExecutionException {
    BlockingQueue arrayBlockingQueue = new ArrayBlockingQueue(
    1);
    ThreadPoolExecutor threadPoolExecutor = new ThreadPoolExecutor(2, 2,
    1000, TimeUnit.MILLISECONDS, arrayBlockingQueue,
    new TestTRejectedExecutionHandler());

    for (int iLoop = 0; iLoop < 100; iLoop++) {
    Future future = threadPoolExecutor.submit(new TestTTask());
    System.out.println(future.get());
    }
    }
    }

    Reply
  4. Here is my Example.

    In this If i call future.get(), then rejectedExecution doesn’t get executed, but if comment that line(future.get()) then it is getting executed.

    Please Suggest a way forward.

    Reply
    • Hi Dushyant,
      get() is blocking call so calling that method after submitting will not give better result since you are waiting the just submitted task. Replace the loop with the below code instead.

       List<Future<String>> list = new ArrayList<>();
              for (int iLoop = 0; iLoop < 10; iLoop++) {
                  Future<String> future = threadPoolExecutor.submit(new TestTTask());
                  list.add(future);
              }
      //getting the results of all submitted task
              for(Future<String> future:list){
                  System.out.println("Thread Name: "+future.get());
              }
      
      
      Reply
  5. Hello

    How would you handle Rejected Task if i use ArrayBlockingQueue and choose to implement my own RejectedExecutionHandler Class.

    Dushyant Sapra

    Reply
  6. Very nice article about Future, Callable and Executor. I wandered here and there for basic information and use, but didn’t find as easiest as this. Thanks Lokesh. Thanks a lot.

    Reply
  7. very very useful information, to know any new subject I will first search in your site. if I didnot find then I go for google search.

    Reply

Leave a Comment

HowToDoInJava

A blog about Java and its related technologies, the best practices, algorithms, interview questions, scripting languages, and Python.