Fork-Join使用的标准范式 ——> Fork/Join的同步用法同时演示返回结果值:统计整形数组中所有元素的和
SumArray
package com.xiangxue.ch2.forkjoin.sum;
import java.util.concurrent.ForkJoinPool;
import java.util.concurrent.RecursiveTask;
import com.xiangxue.tools.SleepTools;
public class SumArray {
private static class SumTask extends RecursiveTask<Integer>{
private final static int THRESHOLD = MakeArray.ARRAY_LENGTH/10;
private int[] src; //表示我们要实际统计的数组
private int fromIndex;//开始统计的下标
private int toIndex;//统计到哪里结束的下标
public SumTask(int[] src, int fromIndex, int toIndex) {
this.src = src;
this.fromIndex = fromIndex;
this.toIndex = toIndex;
}
@Override
protected Integer compute() {
if(toIndex-fromIndex < THRESHOLD) {
int count = 0;
for(int i=fromIndex;i<=toIndex;i++) {
SleepTools.ms(1);//模拟业务处理
count = count + src[i];
}
return count;
}else {
//fromIndex....mid....toIndex
//1...................70....100
int mid = (fromIndex+toIndex)/2;
SumTask left = new SumTask(src,fromIndex,mid);
SumTask right = new SumTask(src,mid+1,toIndex);
invokeAll(left,right);
return left.join()+right.join();
}
}
}
public static void main(String[] args) {
ForkJoinPool pool = new ForkJoinPool();
int[] src = MakeArray.makeArray();
SumTask innerFind = new SumTask(src,0,src.length-1);//new myTask
long start = System.currentTimeMillis();
pool.invoke(innerFind);//同步调用
System.out.println("Task is Running.....");
System.out.println("The count is "+innerFind.join()
+" spend time:"+(System.currentTimeMillis()-start)+"ms");
}
}
SumNormal
package com.xiangxue.ch2.forkjoin.sum;
import com.xiangxue.tools.SleepTools;
public class SumNormal {
public static void main(String[] args) {
int count = 0;
int[] src = MakeArray.makeArray();
long start = System.currentTimeMillis();
for(int i= 0;i<src.length;i++){
SleepTools.ms(1); //模拟业务处理
count = count + src[i];
}
System.out.println("The count is "+count
+" spend time:"+(System.currentTimeMillis()-start)+"ms");
}
}
MakeArray
package com.xiangxue.ch2.forkjoin.sum;
import java.util.Random;
/**
*
*产生整形数组
*/
public class MakeArray {
//数组长度
//public static final int ARRAY_LENGTH = 100000000; //1千万
public static final int ARRAY_LENGTH = 10000; //1万
public static int[] makeArray() {
//new一个随机数发生器
Random r = new Random();
int[] result = new int[ARRAY_LENGTH];
for(int i=0;i<ARRAY_LENGTH;i++){
//用随机数填充数组
result[i] = r.nextInt(ARRAY_LENGTH*3);
}
return result;
}
}
SleepTools
package com.xiangxue.ch2.forkjoin.sum;
import java.util.Random;
/**
*
*产生整形数组
*/
public class MakeArray {
//数组长度
//public static final int ARRAY_LENGTH = 100000000; //1千万
public static final int ARRAY_LENGTH = 10000; //1万
public static int[] makeArray() {
//new一个随机数发生器
Random r = new Random();
int[] result = new int[ARRAY_LENGTH];
for(int i=0;i<ARRAY_LENGTH;i++){
//用随机数填充数组
result[i] = r.nextInt(ARRAY_LENGTH*3);
}
return result;
}
}
Fork/Join的异步用法同时演示不要求返回值:遍历指定目录(含子目录)寻找指定类型文件
package com.xiangxue.ch2.forkjoin;
import java.io.File;
import java.util.ArrayList;
import java.util.List;
import java.util.concurrent.ForkJoinPool;
import java.util.concurrent.RecursiveAction;
/**
*
*类说明:遍历指定目录(含子目录)找寻指定类型文件
*/
public class FindDirsFiles extends RecursiveAction{
private File path;//当前任务需要搜寻的目录
public FindDirsFiles(File path) {
this.path = path;
}
public static void main(String [] args){
try {
// 用一个 ForkJoinPool 实例调度总任务
ForkJoinPool pool = new ForkJoinPool();
FindDirsFiles task = new FindDirsFiles(new File("F:/"));
pool.execute(task);//异步调用
System.out.println("Task is Running......");
Thread.sleep(1);
int otherWork = 0;
for(int i=0;i<100;i++){
otherWork = otherWork+i;
}
System.out.println("Main Thread done sth......,otherWork="+otherWork);
task.join();//阻塞的方法
System.out.println("Task end");
} catch (Exception e) {
e.printStackTrace();
}
}
@Override
protected void compute() {
List<FindDirsFiles> subTasks = new ArrayList<>();
File[] files = path.listFiles();
if(files!=null) {
for(File file:files) {
if(file.isDirectory()) {
subTasks.add(new FindDirsFiles(file));
}else {
//遇到文件,检查
if(file.getAbsolutePath().endsWith("txt")) {
System.out.println("文件:"+file.getAbsolutePath());
}
}
}
if(!subTasks.isEmpty()) {
for(FindDirsFiles subTask:invokeAll(subTasks)) {
subTask.join();//等待子任务执行完成
}
}
}
}
}