首先我们先了解一下Callable接口
Callable接口可以满足我们既能创建线程,又可以有返回值的需求。(Thread类和Runnable接口实现多线程时,不能同时获得返回值。)
经查询,Callable只有一个方法call
实现多线程的方式与Runnable接口一样,都是通过Thread类的有参构造方法传入Runnable接口类型的参数来实现多线程,不同的是,这里传入的是Runnable接口的子类FutureTask对象作为参数,而FutureTask对象中则封装带有返回值的Callable接口实现类。
总而言之,就是Callable产生结果,FutureTask获取结果。
使用步骤如下:
①创建 Callable 接口的实现类,并实现 call() 方法,该 call() 方法将作为线程执行体,并且有返回值;
②创建 Callable 实现类的实例,使用 FutureTask 类来包装 Callable 对象,
该 FutureTask 对象封装了该 Callable 对象的 call() 方法的返回值;
③使用 FutureTask 对象作为 Thread 对象的 target 创建并启动新线程;
④调用 FutureTask 对象的 get() 方法来获得子线程执行结束后的返回值。
练习要求:创建多线程打印斐波那契数列
斐波那契数列(Fibonacci数列)
这个数列从第3项开始,之后的每一项都等于它的前两项数字之和。
这个数列为:
1, 1, 2, 3, 5, 8, 13, 21, 34, 55, 89, 144, 233,377,610,987,1597,2584,4181,6765,10946,17711,28657,46368…
代码如下:
package com.company;
import java.util.concurrent.Callable;
import java.util.concurrent.FutureTask;
import java.util.*;
public class Task {
public static void main(String[] args) throws Exception{
Scanner input =new Scanner(System.in);
int num=input.nextInt();
Function f=new Function();
f.runThread(num);
}
}
class Function {
public void runThread(int num) {
// 在这里开启线程 获取线程执行的结果
ThreadCallable tc=new ThreadCallable();
tc.number=num;
FutureTask<Integer> ft=new FutureTask<Integer>(tc);
new Thread(ft).start();
try{
System.out.print("线程的返回值为:"+ft.get());
}catch(Exception e){
e.printStackTrace();
}
}
}
/* 在这里实现Callable接口及方法 */
class ThreadCallable implements Callable{
public int number;
public Integer call()throws Exception{
int an;
double a=(1+Math.sqrt(5))/2;
double b=(1-Math.sqrt(5))/2;
double c=1/(Math.sqrt(5));
an=(int)(c*(Math.pow(a,number)-Math.pow(b,number)));
return an;
}
}
运行结果: