gpt4 book ai didi

java - 为什么 Java 并发处理不能处理新实例化的对象,而可以处理同一类的反序列化对象?

转载 作者:行者123 更新时间:2023-11-30 08:13:26 30 4
gpt4 key购买 nike

我正在使用java.util.concurrent.ExecutorService对所有可用的处理资源执行并发计算。在下面的代码中,MyProcessor 类的实例在其 performParallelProcessing 方法中创建了许多 ProcessingExecutor 类实例,并将它们提交给 ExecutorService 实例期望获得相应的回调。

处理发生在ProcessingExecutor类的performProcessing方法中。我用于处理的数据是ComputationData 类的对象实例。它们可以从文件系统中检索(如果存在序列化数据),也可以初始化为新实例。

问题是这样的:

如果从文件系统反序列化ComputationData对象实例,并发处理将按照我的预期执行。它在所有处理核心上并行运行,占用100%的处理资源。

如果ComputationData对象实例是新初始化的,并发处理不会按我的预期执行。它的运行就像单线程执行一样,占用大约 15% 的处理资源。

正如我猜测的那样,我新初始化的 ComputationData 对象实例出了问题。但我不知道它们可能出了什么问题,也不知道为什么并发对它们不起作用,而它对它们的序列化->反序列化版本起作用。任何提示或想法将不胜感激。

public class MyProcessor {
private boolean processingFinished = false;

public void performParallelProcessing(){
int count = 0;
boolean continueProcessing = true;

int nrOfProcessors = Runtime.getRuntime().availableProcessors();
ExecutorService es = Executors.newFixedThreadPool(nrOfProcessors);

while (continueProcessing){
ProcessingExecutor task = new ProcessingExecutor(count);
task.setCaller(this);
es.submit(task);
count++;

if (!processingFinished){
try{
Thread.sleep(50);
}
catch(SecurityException | InterruptedException e){
//Exception handling
}
}
else{
continueProcessing = false;
}
}
}

public void callBack(ProcessingResult result) {
if(result.allDataProcessed()){
this.processingFinished = true;
}
}
}

public class ProcessingExecutor implements Callable {
private MyProcessor processor;
private int count;

public ProcessingExecutor(int count){
this.count = count;
}

public Object call() {
ProcessingResult result = null;
try {
result = performProcessing();
}
catch (SecurityException e) {
//Exception handling
}

processor.callBack(result);
return null;
}

public void setCaller(MyProcessor processor) {
this.processor = processor;
}

public MyProcessor getCaller() {
return this.processor;
}

private ProcessingResult performProcessing(){
ComputationData data = null;

if(serializedDataExist()){
data = getSerializedData(count);
}
else{
data = initializeNewData(count);
}

ProcessingResult result = new ProcessingResult(data, count);
return result;
}

private ComputationData getSerializedData(int count){
ComputationData data = null;
// code to retrieve a ComputationData object from the file system
// based on 'count' value.
return data;
}

private ComputationData initializeNewData(int count){
ComputationData data = null;
// code to initialize a new instance of ComputationData class
// based on 'count' value.
return data;
}

private boolean serializedDataExist(){
boolean dataFound = false;
// code to verify whether serialized ComputationData objects are
// present on the file system.
return dataFound;
}
}

最佳答案

为什么需要Thread.sleep(50)?这就是使并发执行变成顺序执行的原因,特别是如果每​​次计算 <= 50 毫秒。我的猜测是,反序列化时间 + 计算时间超过 50 毫秒,这就是为什么在反序列化对象场景中,您有更多的 CPU Activity ,因为您实际上有多个任务在执行器线程中同时运行。您应该尝试不使用 Thread.sleep(50) 或至少使用更小的超时。

关于java - 为什么 Java 并发处理不能处理新实例化的对象,而可以处理同一类的反序列化对象?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/30017372/

30 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com