执行所有线程之前的方法 returns,即使使用了 executor.awaitTermination
Method returns before executing all threads even though executor.awaitTermination is used
我有一个方法需要多个线程才能工作,然后相应地为每个线程执行 运行() 方法,如下所示
public static Map<String, Integer> execute(int thread_count) {
ExecutorService executor = Executors.newFixedThreadPool(thread_count);
File folder = new File("logFiles/");
Collection<File> files = FileUtils.listFiles(folder, null, true);
for(File file : files){
//For rach file in folder execute run()
System.out.println(file.getName());
executor.submit(new Runner((file.getAbsolutePath())));
}
executor.shutdown();
try {
executor.awaitTermination(1, TimeUnit.DAYS);
} catch (InterruptedException e) {
System.out.println("Exception "+ e + " in CountLines.execute()");
}
for(Map.Entry<String, Integer> entry: Runner.lineCountMap.entrySet()){
System.out.println(entry.getKey() + " : : " + entry.getValue());
}
return Runner.lineCountMap;// printing after all the threads finish executing
}
而运行方法定义如下:
public void run() {
try {
count = countLines(file);//get number of lines in file
} catch (IOException e) {
System.out.println("Exception "+ e + " in Runner.run()");
}
//count number of lines in each file and add to map
lineCountMap.put(file, count);
}
因为我在上面的 execute() 方法中使用了 executor.awaitTermination,所以我希望我的 lineCountMap 填充所有文件名作为键,行数作为值。但是似乎在执行所有线程之前返回了 lineCountMap。
For the following files:
logtest.2014-07-04.log
logtest.2014-07-02.log
logtest.2014-07-01.log
logtest.2014-07-03.log
Expected Output:
lineCountMap:
/logtest.2014-07-01.log : : 4
/logtest.2014-07-02.log : : 8
/logtest.2014-07-03.log : : 2
/logtest.2014-07-04.log : : 1
Actual Output:
lineCountMap:
/logtest.2014-07-01.log : : 4
/logtest.2014-07-03.log : : 2
/logtest.2014-07-04.log : : 0
此处 我缺少 /logtest.2014-07-02.log 的内容以及 /logtest.2014-07-04.log 的值为1时显示0
将 lineCountMap
更改为 ConcurrentHashMap
解决了问题。感谢 Oliver Croisier 在评论部分讨论的解决方案。
我有一个方法需要多个线程才能工作,然后相应地为每个线程执行 运行() 方法,如下所示
public static Map<String, Integer> execute(int thread_count) {
ExecutorService executor = Executors.newFixedThreadPool(thread_count);
File folder = new File("logFiles/");
Collection<File> files = FileUtils.listFiles(folder, null, true);
for(File file : files){
//For rach file in folder execute run()
System.out.println(file.getName());
executor.submit(new Runner((file.getAbsolutePath())));
}
executor.shutdown();
try {
executor.awaitTermination(1, TimeUnit.DAYS);
} catch (InterruptedException e) {
System.out.println("Exception "+ e + " in CountLines.execute()");
}
for(Map.Entry<String, Integer> entry: Runner.lineCountMap.entrySet()){
System.out.println(entry.getKey() + " : : " + entry.getValue());
}
return Runner.lineCountMap;// printing after all the threads finish executing
}
而运行方法定义如下:
public void run() {
try {
count = countLines(file);//get number of lines in file
} catch (IOException e) {
System.out.println("Exception "+ e + " in Runner.run()");
}
//count number of lines in each file and add to map
lineCountMap.put(file, count);
}
因为我在上面的 execute() 方法中使用了 executor.awaitTermination,所以我希望我的 lineCountMap 填充所有文件名作为键,行数作为值。但是似乎在执行所有线程之前返回了 lineCountMap。
For the following files:
logtest.2014-07-04.log
logtest.2014-07-02.log
logtest.2014-07-01.log
logtest.2014-07-03.log
Expected Output:
lineCountMap:
/logtest.2014-07-01.log : : 4
/logtest.2014-07-02.log : : 8
/logtest.2014-07-03.log : : 2
/logtest.2014-07-04.log : : 1
Actual Output:
lineCountMap:
/logtest.2014-07-01.log : : 4
/logtest.2014-07-03.log : : 2
/logtest.2014-07-04.log : : 0
此处 我缺少 /logtest.2014-07-02.log 的内容以及 /logtest.2014-07-04.log 的值为1时显示0
将 lineCountMap
更改为 ConcurrentHashMap
解决了问题。感谢 Oliver Croisier 在评论部分讨论的解决方案。