我有如下代码。在循环中,它正在执行方法“process”。它按顺序运行。我想并行运行这个方法,但它应该在循环中完成,以便我可以在下一行中求和。即使它并行运行,所有函数都应该在第二个for循环执行之前完成。
如何在Jdk1.7中解决这个问题而不是JDK1.8版本?
public static void main(String s[]){
int arrlen = 10;
int arr[] = new int[arrlen] ;
int t =0;
for(int i=0;i<arrlen;i++){
arr[i] = i;
t = process(arr[i]);
arr[i] = t;
}
int sum =0;
for(int i=0;i<arrlen;i++){
sum += arr[i];
}
System.out.println(sum);
}
public static int process(int arr){
return arr*2;
}
答案 0 :(得分:3)
以下示例可能会对您有所帮助。我使用fork / join框架来做到这一点。
对于像你的例子那样的小数组大小,传统的方法可能会更快,我怀疑fork / join方式会花费更多的时间。但是对于更大的大小或进程,fork / join框架是合适的。甚至java 8并行流也使用fork / join框架作为底层基础。
def response(message):
return {
"dialogAction":{
"type":"Close",
"fulfillmentState":"Fulfilled",
"message":{
"contentType":"PlainText",
"content":message
}
}
}
return response(str(logging_info_object))
您的主要课程如下所示
public class ForkMultiplier extends RecursiveAction {
int[] array;
int threshold = 3;
int start;
int end;
public ForkMultiplier(int[] array,int start, int end) {
this.array = array;
this.start = start;
this.end = end;
}
protected void compute() {
if (end - start < threshold) {
computeDirectly();
} else {
int middle = (end + start) / 2;
ForkMultiplier f1= new ForkMultiplier(array, start, middle);
ForkMultiplier f2= new ForkMultiplier(array, middle, end);
invokeAll(f1, f2);
}
}
protected void computeDirectly() {
for (int i = start; i < end; i++) {
array[i] = array[i] * 2;
}
}
}
答案 1 :(得分:0)
你基本上需要使用自Java 1.5以来存在的Executors和Futures组合(见Java Documentation)。
在下面的示例中,我创建了一个主类,它使用另一个辅助类,其作用类似于要并行化的处理器。
主要课程分为3个步骤:
由于说明的原因,我已经放了一些日志,更重要的是,我在每个进程中放置了一个随机的等待时间'业务逻辑,模拟了一个由Process类运行的耗时算法
每个进程的最长等待时间是2秒,这也是步骤2的最长等待时间,即使您增加了并行任务的数量(只需尝试将以下代码的变量totalTasks
更改为测试它。)
这里是主类:
package com.example;
import java.util.ArrayList;
import java.util.concurrent.ExecutionException;
import java.util.concurrent.ExecutorService;
import java.util.concurrent.Executors;
import java.util.concurrent.Future;
public class Main
{
public static void main(String[] args) throws InterruptedException, ExecutionException
{
int totalTasks = 100;
ExecutorService newFixedThreadPool = Executors.newFixedThreadPool(totalTasks);
System.out.println("Step 1 - Starting parallel tasks");
ArrayList<Future<Integer>> tasks = new ArrayList<Future<Integer>>();
for (int i = 0; i < totalTasks; i++) {
tasks.add(newFixedThreadPool.submit(new Process(i)));
}
long ts = System.currentTimeMillis();
System.out.println("Step 2 - Wait for processes to finish...");
boolean tasksCompleted;
do {
tasksCompleted = true;
for (Future<Integer> task : tasks) {
if (!task.isDone()) {
tasksCompleted = false;
Thread.sleep(10);
break;
}
}
} while (!tasksCompleted);
System.out.println(String.format("Step 2 - End in '%.3f' seconds", (System.currentTimeMillis() - ts) / 1000.0));
System.out.println("Step 3 - All processes finished to run, let's collect results...");
Integer sum = 0;
for (Future<Integer> task : tasks) {
sum += task.get();
}
System.out.println(String.format("Total final sum is: %d", sum));
}
}
这里是Process类:
package com.example;
import java.util.concurrent.Callable;
public class Process implements Callable<Integer>
{
private Integer value;
public Process(Integer value)
{
this.value = value;
}
public Integer call() throws Exception
{
Long sleepTime = (long)(Math.random() * 2000);
System.out.println(String.format("Starting process with value %d, sleep time %d", this.value, sleepTime));
Thread.sleep(sleepTime);
System.out.println(String.format("Stopping process with value %d", this.value));
return value * 2;
}
}
希望这有帮助。