JUC详解 -> ForkJoin详解
什么是ForkJoin?
- JDK 1.7后
- 并行执行任务,提高效率,大数据量!
- 大数据:Map Reduce,把大任务拆分为小任务
- ForkJoin特点:工作窃取
- 这个里面维护的都是双端队列
ForkJoin操作
//求和计算的任务
import java.util.concurrent.RecursiveTask;
/**
* 如何使用ForkJoin
* 1.ForkJoinPool 通过它来执行
* 2.计算任务forkjoin.execute(ForkJoinTask<?> task)
* 3.计算任务继承ForkJoinTask
*/
public class ForkJoinDemo extends RecursiveTask<Long> {
private Long start;
private Long end;
//临界值
private Long temp = 10000L;
public ForkJoinDemo(Long start, Long end){
this.start = start;
this.end = end;
}
@Override
protected Long compute() {
if((end - start)<temp){
Long sum = 0L;
for(Long i = start; i <= end; i++){
sum = sum + i;
}
return sum;
}else{
//forkJoin分支合并计算
long middle = (start + end) / 2;//中间值
ForkJoinDemo task1 = new ForkJoinDemo(start, middle);
task1.fork();//拆分任务,把任务压入线程队列
ForkJoinDemo task2 = new ForkJoinDemo(middle + 1, end);
task2.fork();
return task1.join() + task2.join();
}
}
}
import java.util.concurrent.ExecutionException;
import java.util.concurrent.ForkJoinPool;
import java.util.concurrent.ForkJoinTask;
import java.util.stream.LongStream;
public class Test {
public static void main(String[] args) throws ExecutionException, InterruptedException {
//test1();
//test2();
test3();
}
public static void test1(){
Long sum = 0L;
long start = System.currentTimeMillis();
for (Long i = 1L; i < 10_0000_0000; i++) {
sum = sum + i;
}
long end = System.currentTimeMillis();
System.out.println("sum= " + "时间:"+ (end - start)); //9949
}
public static void test2() throws ExecutionException, InterruptedException {
long start = System.currentTimeMillis();
ForkJoinPool forkJoinPool = new ForkJoinPool();
ForkJoinTask<Long> task = new ForkJoinDemo(0L, 10_0000_0000L);
ForkJoinTask<Long> submit = forkJoinPool.submit(task);//提交任务
Long sum = submit.get();
long end = System.currentTimeMillis();
System.out.println("sum= " + "时间:"+ (end - start)); //4055
}
public static void test3(){
long start = System.currentTimeMillis();
//Stream
long sum = LongStream.rangeClosed(1L, 10_0000_0000).parallel().reduce(0, Long::sum); //368
long end = System.currentTimeMillis();
System.out.println("sum= " + "时间:"+ (end - start));
}
}
System.currentTimeMillis();
System.out.println("sum= " + “时间:”+ (end - start));
}
}