runnable和callable的区别主要在于它们的用途和实现方式。
主要区别:
- runnable指的是一个对象能够被执行,而callable指的是一个函数或方法能够被调用。
- runnable通常指实现了Runnable接口的对象,它通过实现接口中的run()方法来定义可执行代码。而callable则通常指实现了Callable接口的函数或方法,它通过实现接口中的call()方法来定义可被调用的代码。
- runnable对象可以通过创建线程来执行,而callable则可以通过使用ExecutorService执行或者作为FeatureTask的参数。
runnable的执行 , 作为thread的参数
public class MyRunnable implements Runnable {
@Override
public void run() {
// 在这里定义可在线程中执行的代码
}
}
MyRunnable myRunnable = new MyRunnable();
Thread thread = new Thread(myRunnable);
thread.start();
or
Thread thread = new Thread(new Runnable() {
@Override
public void run() {
// 在这里定义可在线程中执行的代码
}
});
thread.start();
callable的执行,被ExecutorService执行or作为FeatureTask的参数
public class MyCallable implements Callable<T> {
@Override
public T call() throws Exception {
// 在这里定义可被调用的代码
}
}
MyCallable myCallable = new MyCallable();
ExecutorService executor = Executors.newSingleThreadExecutor();
Future<T> future = executor.submit(myCallable);
T result = future.get();
or
ExecutorService executor = Executors.newSingleThreadExecutor();
Future<T> future = executor.submit(new Callable<T>() {
@Override
public T call() throws Exception {
// 在这里定义可被调用的代码
}
});
T result = future.get();
使用FeatureTask
Callable<Process> task = () -> {
// 执行异步任务
Runtime runtime = Runtime.getRuntime();
Process process = runtime.exec("/Users/mac/Desktop/qc-java-runtime/src/main/java/com/qc/runtime/shell.sh");
return process;
};
// 将Callable包装成FutureTask
FutureTask<Process> future = new FutureTask<>(task);
// 启动新线程来执行异步任务
new Thread(future).start();
// 获取异步任务的结果
Process result = future.get();
System.out.println(result);