Java Future.get()不返回

Java Future.get()不返回,java,multithreading,concurrency,Java,Multithreading,Concurrency,我有以下代码: public class Test { List<Future> future = new ArrayList<Future>(); public static void main(String args[]) throws Exception { Adapter b1 = new Adapter(); final ExecutorService threadPool = Executors.newCachedThrea

我有以下代码:

public class Test {
   List<Future> future = new ArrayList<Future>();

   public static void main(String args[]) throws Exception {

     Adapter b1 = new Adapter();
     final ExecutorService threadPool = Executors.newCachedThreadPool();

      for(//iterate for number of files) {  
         while(data exists in file) {
            //Call a function to process and update values in db 
            future.add(threadPool.submit(new Xyz(b1)));
            //read next set of data in file;
         }
       }

      try {
         for(Future f: future) { 
            f.get(); 
         }
      }
      catch(Exception e) {
         throw e;
      }    
   }
}

class Xyz implements Runnable {
   private Adapter a1;

   public Xyz(Adapter al) {
      this.a1=a1;
   }

   @Override
   public void run() {
      try { 
         a1.abc();
      } catch (Exception e) {
          throw new RuntimeException(e);
      } 
   }
}
公共类测试{
List future=new ArrayList();
公共静态void main(字符串args[])引发异常{
适配器b1=新适配器();
final ExecutorService threadPool=Executors.newCachedThreadPool();
对于(//迭代文件数){
while(数据存在于文件中){
//调用函数来处理和更新数据库中的值
future.add(threadPool.submit)(新的Xyz(b1));
//读取文件中的下一组数据;
}
}
试一试{
(未来f:未来){
f、 get();
}
}
捕获(例外e){
投掷e;
}    
}
}
类Xyz实现可运行{
专用适配器a1;
公共Xyz(适配器al){
这个。a1=a1;
}
@凌驾
公开募捐{
试试{
a1.abc();
}捕获(例外e){
抛出新的运行时异常(e);
} 
}
}
当文件数为1时(循环运行1次),代码运行正常

但是,当文件数量增加时,代码永远不会从
future.get()
方法返回

只是出于好奇。。我需要关闭某个地方的执行者吗

是的,这可能就是问题所在。每个
Future.get()
都将阻塞,直到相应的任务完成,然后在所有任务完成后,您的
main
线程将退出。但是java进程不会退出,因为线程池线程在后台仍然处于活动状态。您应该在完成executor之后关闭它,这很可能是
main
方法中的最后一件事


我还注意到,您提交的许多任务都封装了相同的
适配器
实例,并且都调用了它的
abc()
方法-检查其中没有任何内容在多个线程中同时调用时会死锁。

您的
可调用::调用
/
可运行::运行
不会返回。否则,相应的未来不会受阻

附加executor.shutdown或
future.cancel将使用
InterruptedException
停止线程处理您提交的对象,但是否捕获它取决于您。您负责停止提交的作业

当你向一个
CachedExecutor
提交数千个可调用/可运行文件时,它可能会产生太多的线程,以至于你的机器变得如此缓慢,以至于你认为这需要永远的时间。但你会注意到的

在处理未定义数量的可并行化任务时,我建议使用
FixedThreadPool
,其中的线程数量不超过cpu核心


编辑:因此,当您在
a1.abc()处设置断点时您是否知道您正在嵌套循环中调用
newCachedThreadPool
?您确定futures run方法的实现中没有问题吗?死锁可能是因为多个future尝试访问相同的独占资源而发生的?Philip,如果我注释掉future,evrything运行良好。get()无论什么
a1。abc()
正在执行块,而您的
future.get()
相应地调用块。edwin,我是多线程的新手,调用newCachedThreadPool会有问题吗?我做了一些更改,比如publicstaticvoidmain(stringargs[])抛出异常{adapterb1=newadapter();finalexecutorservice threadPool=Executors.newCachedThreadPool();//rest是相同的,但问题仍然是相同的!!但它对单个文件非常有效,对多个文件无效,我不理解这种行为。