Clean • Professional
Callable and Future are important parts of Java’s Concurrency API. They help you run tasks in the background and get results safely once the task is completed.
If you want to execute a task asynchronously and receive a result later, then Callable and Future are the best tools in Java.
Callable is a functional interface that represents a task that can be executed asynchronously and returns a result.
It is similar to Runnable, but with two important differences:
Runnable, which cannot return any value, Callable returns a value of type V.Callable can throw checked exceptions, whereas Runnable cannot.Key Points:
java.util.concurrentSyntax:
@FunctionalInterface
publicinterfaceCallable<V> {
Vcall()throws Exception;
}
In simple words:
Callable = Runnable + Returns a Result + Can Throw Exceptions
import java.util.concurrent.Callable;
import java.util.concurrent.ExecutorService;
import java.util.concurrent.Executors;
import java.util.concurrent.Future;
publicclassCallableExample {
publicstaticvoidmain(String[] args)throws Exception {
// Create a thread pool
ExecutorServiceexecutor= Executors.newFixedThreadPool(2);
// Create a Callable task
Callable<Integer> task = () -> {
intsum=0;
for (inti=1; i <=5; i++) {
sum += i;
}
return sum;// return result
};
// Submit task to executor
Future<Integer> futureResult = executor.submit(task);
// Get result from Future
Integerresult= futureResult.get();// waits until task completes
System.out.println("Sum: " + result);
// Shutdown executor
executor.shutdown();
}
}
Sample Output:
Sum: 15
—> Notice how the task returns a result through the Future object, unlike Runnable which doesn’t return anything.
1. Can Return a Result
Runnable, Callable tasks return a value.2. Can Throw Checked Exceptions
Callable can throw exceptions, which allows better error handling in multithreaded tasks.3. Works with ExecutorService
ExecutorService, allowing asynchronous task execution without manual thread management.4. Supports Future for Results
5. Ideal for Long-Running Tasks
You should use Callable instead of Runnable in situations where:
Runnable and Callable are interfaces used in Java to define tasks that run in separate threads. While both are part of Java’s concurrency mechanism, they are used in different situations.
| Feature | Runnable | Callable |
|---|---|---|
| Purpose | Used to define a simple task that runs in a separate thread. It is mainly for executing logic without expecting any output. | Used to define a task that runs in a separate thread and returns a result after execution. |
| Method Name | run() | call() |
| Method Signature | void run() – does not return anything. | V call() – returns a value of type V. |
| Return Value | Cannot return any value from the thread. | Returns a result after task completion. |
| Checked Exceptions | Cannot throw checked exceptions. All exceptions must be handled inside the run() method. | Can throw checked exceptions, which are handled when calling Future.get(). |
| Result Handling | Not possible directly. You must use shared variables or other complex techniques. | Result is handled cleanly and safely using a Future object. |
| ExecutorService Support | Supported. Can be submitted using executor.submit(Runnable). | Supported. Submitted using executor.submit(Callable) and returns a Future. |
| Future Required | Not required because no result is produced. | Required to retrieve the result or handle exceptions. |
| Asynchronous Execution | Yes, runs asynchronously when executed in a thread or ExecutorService. | Yes, runs asynchronously and provides a future result. |
| Exception Handling Style | Manual try–catch inside the task. | Centralized exception handling via Future.get(). |
| Flexibility | Limited functionality, suitable for basic tasks. | More flexible and powerful for real-world applications. |
| Java Version Introduced | Since Java 1.0 | Introduced in Java 5 (with java.util.concurrent). |
| Best Use Case | Fire-and-forget tasks like logging, background cleanup, sending emails. | Tasks that need results such as calculations, API calls, database queries. |
| Complexity Level | Simple and lightweight. | Slightly more complex but more powerful and scalable. |
Future represents the result of an asynchronous computation.
It allows you to:
Key Points:
java.util.concurrentCallable or Runnable tasksCommon Methods:
| Method | Description |
|---|---|
get() | Waits for the task to finish and returns the result |
isDone() | Checks if the task has completed |
cancel(boolean) | Cancels the task |
isCancelled() | Checks if the task was cancelled |
Example: Using Future
import java.util.concurrent.Callable;
import java.util.concurrent.ExecutorService;
import java.util.concurrent.Executors;
import java.util.concurrent.Future;
publicclassFutureExample {
publicstaticvoidmain(String[] args)throws Exception {
ExecutorServiceexecutor= Executors.newFixedThreadPool(2);
Callable<String> task = () -> {
Thread.sleep(500);// simulate work
return"Task Completed!";
};
// Submit task and get a Future
Future<String> future = executor.submit(task);
System.out.println("Task submitted, waiting for result...");
// Check if task is done
if(!future.isDone()){
System.out.println("Task is still running...");
}
// Get the result
Stringresult= future.get();
System.out.println("Result: " + result);
executor.shutdown();
}
}
Sample Output:
Task submitted, waitingfor result...
Task is still running...
Result:Task Completed!
Explanation:
Future.get() waits for the task to complete and returns the result.isDone() allows you to check the task status before retrieving the result.ExecutorService handles the threads, making asynchronous execution safe and efficient.shutdown() on ExecutorService| Feature | Callable | Future |
|---|---|---|
| Purpose | Represents a task that can be executed asynchronously and returns a result. | Represents the result of an asynchronous computation. |
| Returns a Value | Yes – Callable tasks return a value of type V. | Future stores or retrieves the result of a Callable or Runnable task. |
| Exception Handling | Can throw checked exceptions inside the task. | Cannot throw exceptions itself; you can handle exceptions when calling get(). |
| Usage | Submitted to an ExecutorService using submit(). | Obtained as the return value when a Callable or Runnable is submitted to an ExecutorService. |
| Role | Defines the task logic that produces a result. | Manages the result of the task and provides methods to get the result, check status, or cancel. |
| Methods | call() – Contains task logic. | get(), isDone(), cancel(), isCancelled() – To manage and retrieve the result. |
If you are learning ExecutorService, then Callable & Future are must-know concepts for modern Java development.