fork/join的使用
1、创建一个ForkJoinPool,forkjoin池。
ForkJoinPool forkJoinPool = new ForkJoinPool();
2、创建一个task任务,任务继承自RecursiveTask<Integer>,Integer表示返回结果的类型
CountTask task = new CountTask(1, 4);
3、用这个forkjoin池提交task, 返回一个Future类型的结果
Future<Integer> result = forkJoinPool.submit(task);
在任务task重写的compute() 方法中,如果,任务规模过大,需要创建子任务,子任务的执行使用subTask.fork(),子任务结果的返回使用subTask.join().
<-------------------------------------------------------------------------分割线--------------------------------------------------------------------------->
第一步分割任务。首先我们需要有一个fork类来把大任务分割成子任务,有可能子任务还是很大,所以还需要不停的分割,直到分割出的子任务足够小。
第二步执行任务并合并结果。分割的子任务分别放在双端队列里,然后几个启动线程分别从双端队列里获取任务执行。子任务执行完的结果都统一放在一个队列里,启动一个线程从队列里拿数据,然后合并这些数据。
- public class CountTaskTmp extends RecursiveTask<Integer>{
- private static final int THRESHOLD = 2;
- private int start;
- private int end;
- public CountTaskTmp(int start, int end) {
- this.start = start;
- this.end = end;
- }
- @Override
- protected Integer compute() {
- int sum = 0;
- boolean canCompute = (end - start) <= THRESHOLD;
- if (canCompute) {
- for (int i = start; i <= end; i++)
- sum += i;
- } else {
- //如果任务大于阀值,就分裂成两个子任务计算
- int mid = (start + end) / 2;
- CountTask leftTask = new CountTask(start, mid);
- CountTask rightTask = new CountTask(mid+1, end);
- //执行子任务
- leftTask.fork();
- rightTask.fork();
- //等待子任务执行完,并得到结果
- int leftResult = (int)leftTask.join();
- int rightResult = (int)rightTask.join();
- sum = leftResult + rightResult;
- }
- return sum;
- }
- public static void main(String[] args) {
- ForkJoinPool forkJoinPool = new ForkJoinPool();
- //生成一个计算资格,负责计算1+2+3+4
- CountTask task = new CountTask(1, 4);
- Future<Integer> result = forkJoinPool.submit(task);
- try {
- System.out.println(result.get());
- } catch (Exception e) {
- }
- }
- }