1定义分而治之:适合大问题分解成规模相同无联系的小问题,(如果有联系就是动态规划),比如排序中的分治算法;其实快速,二分也可以分治
这个代码时利用forkjoin实现归并排序
package cn.enjoyedu.ch2.forkjoin.sort;
import cn.enjoyedu.ch2.forkjoin.sum.MakeArray;
import java.util.concurrent.ForkJoinPool;
import java.util.concurrent.RecursiveTask;
public class test {
//归并-合并
static void merge(int[] arr, int left, int mid, int right) {
int[] temp = new int[right - left + 1];
int i = 0;
int p1 = left;
int p2 = mid + 1;
while (p1 <= mid && p2 <= right) {
temp[i++] = arr[p1] <= arr[p2] ? arr[p1++] : arr[p2++];
}
while (p1 <= mid) {
temp[i++] = arr[p1++];
}
while (p2 <= right) {
temp[i++] = arr[p2++];
}
for (int j = 0; j < temp.length; j++) {
arr[left + j] = temp[j];
}
}
public static void main(String[] args) {
ForkJoinPool pool = new ForkJoinPool();
int[] arr = MakeArray.makeArray();
SumTaskTest s = new SumTaskTest(arr, 0, arr.length - 1);
System.out.println("============================================");
long start = System.currentTimeMillis();
pool.invoke(s);
System.out.println(" spend time:" + (System.currentTimeMillis() - start) + "ms");
//展示排序后的结果
// for (int i = 0; i < arr.length; i++) {
// System.out.println(arr[i]);
// }
}
private static class SumTaskTest extends RecursiveTask<Void> {
int arr[];
int left;
int right;
public SumTaskTest(int[] arr, int left, int right) {
this.arr = arr;
this.left = left;
this.right = right;
}
@Override
protected Void compute() {
int mid = (left + right) / 2;
if (left == right) {
merge(arr, left, mid, right);
} else {
SumTaskTest s1 = new SumTaskTest(arr, left, mid);
SumTaskTest s2 = new SumTaskTest(arr, mid + 1, right);
invokeAll(s1,s2);
s1.join();
s2.join();
merge(arr, left, mid, right);
}
return null;
}
}
}
=========================创建数组的工具类==================
package cn.enjoyedu.ch2.forkjoin.sum;
import java.util.Random;
public class MakeArray {
//数组长度
public static final int ARRAY_LENGTH = 40000000;
public final static int THRESHOLD = 47;
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;
}
}
2 forkjoin的语法
1. RecursiveAction,用于没有返回结果的任务 2. RecursiveTask,用于有返回值的任务 task 要通过 ForkJoinPool 来执行,使用 submit 或 invoke 提交,两者的区
别是:invoke 是同步执行,调用之后需要等待任务完成,才能执行后面的代码; submit 是异步执行。 join()和 get 方法当任务完成的时候返回计算结果。
1定义:闭锁或者叫发令枪,当计数器为0时,在计数器上等待的线程就可以执行了
2以用场景:当想测试最大并发数时
3语法coutdownlatch.countDown() 计数器减一
4例子
原文:https://www.cnblogs.com/xiaoshahai/p/13083054.html