我有一段代码我想并行化,因为它们是独立的操作 -
List<StockQuote> topGainers = new ArrayList<StockQuote>();
JSONObject jsonObject = (JSONObject)new JSONParser().parse(
new InputStreamReader(response.getEntity().getContent(), "UTF-8"));
JSONArray dataArray = (JSONArray) jsonObject.get("data");
//Parallelize the for loop
for(int iter=0;iter<dataArray.size();iter++) {
JSONObject temp = (JSONObject) dataArray.get(iter);
System.out.println(temp.get("symbol"));
//getQuote function has network calls.
//Serial implementation makes it take too much time
topGainers.add(this.getQuote((String)temp.get("symbol")));
}
return topGainers;
如何将这段代码并行化? ArrayList及其Add操作线程是否安全?
我试过了 -
int size = dataArray.size();
ForkJoinPool forkJoinPool = new ForkJoinPool(size);
forkJoinPool.submit(() ->
IntStream.range(1, size).parallel().filter( (IntPredicate)i -> {
JSONObject temp = (JSONObject) dataArray.get(i);
System.out.println(temp.get("symbol"));
try {
System.out.println(temp.get("symbol"));
topGainers.add(this.getQuote((String)temp.get("symbol")));
} catch (Exception e) {
// TODO Auto-generated catch block
e.printStackTrace();
}
return true;}));
我将topGainers数组视为空
答案 0 :(得分:0)
ArrayList
不是Synchronized
集合。因此,ArrayList#add
不是线程安全的。使用CopyOnWriteArrayList
代替线程安全。 Java-8为我们提供了一些优秀的功能,其中一个是parallelStream
集合。所以你可以利用它。但是,如果能为您带来更多好处,您可以自由创建自己的线程池并执行任务。
以下示例可以帮助您
CopyOnWriteArrayList<StockQuote> topGainers = new CopyOnWriteArrayList<>();
dataArray.parallelStream().forEach(e->{
JSONObject temp = (JSONObject) dataArray.get(iter);
System.out.println(temp.get("symbol"));
//getQuote function has network calls.
//Serial implementation makes it take too much time
topGainers.add(this.getQuote((String)temp.get("symbol")));
});
您的云也使用Collections#synchronizedList
。
从评论中的问题1回答:dataArray.parallelStream().forEach
将并行迭代列表。
通过评论回答你的问题2:
dataArray.parallelStream().forEach(e->{
JSONObject temp = (JSONObject) dataArray.get(iter);
System.out.println(temp.get("symbol"));
//getQuote function has network calls.
//Serial implementation makes it take too much time
if (some condition here) {
throw new YourException("Your exception messge");
}
topGainers.add(this.getQuote((String)temp.get("symbol")));
});