Warning: file_get_contents(/data/phpspider/zhask/data//catemap/9/java/356.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
Java 程序永远不会结束,但线程池声明将关闭_Java_Multithreading_Ojdbc - Fatal编程技术网

Java 程序永远不会结束,但线程池声明将关闭

Java 程序永远不会结束,但线程池声明将关闭,java,multithreading,ojdbc,Java,Multithreading,Ojdbc,我遇到了一个多线程程序的问题 我需要模拟许多人试图在同一时间预订同一航班,不使用锁 所以我制作了一个ExecutorService,并使用它来汇集线程,这样我就可以同时进行许多尝试 但问题是,程序在打印出所有结果之前就已经结束了,它只是坐在那里永远运行。我试图进入所有其他利用数据库连接的类,并简单地手动关闭它们。不走运 package dbassignment4; import java.util.ArrayList; import java.util.List; impor

我遇到了一个多线程程序的问题

我需要模拟许多人试图在同一时间预订同一航班,不使用锁

所以我制作了一个ExecutorService,并使用它来汇集线程,这样我就可以同时进行许多尝试

但问题是,程序在打印出所有结果之前就已经结束了,它只是坐在那里永远运行。我试图进入所有其他利用数据库连接的类,并简单地手动关闭它们。不走运

package dbassignment4;

   import java.util.ArrayList;
   import java.util.List;
   import java.util.concurrent.ExecutionException;
   import java.util.concurrent.ExecutorService;
   import java.util.concurrent.Future;
   import java.util.concurrent.LinkedBlockingQueue;
   import java.util.concurrent.RejectedExecutionException;
   import java.util.concurrent.ThreadPoolExecutor;
   import java.util.concurrent.TimeUnit;

   /**
    *
    * @author Vipar
    */
   public class Master{

   private static final int POOL_SIZE = 50;
   public static boolean planeIsBooked = false;
   /**
    * @param args the command line arguments
    */
   public static void main(String[] args) {

       int success = 0;
       int seatNotReserved = 0;
       int seatNotReservedByCustomerID = 0;
       int reservationTimeout = 0;
       int seatIsOccupied = 0;
       int misc = 0;

       HelperClass.clearAllBookings("CR9");
       Thread t = new Thread(new DBMonitor("CR9"));
       long start = System.nanoTime();
       //HelperClass.clearAllBookings("CR9");
       ExecutorService pool = new ThreadPoolExecutor(
               POOL_SIZE, POOL_SIZE,
               0L,
               TimeUnit.MILLISECONDS,
               new LinkedBlockingQueue<Runnable>(POOL_SIZE));
       int threadsStarted = 0;
       List<Future<Integer>> results = new ArrayList<>();
       long id = 1;
       t.start();
       while(planeIsBooked == false) {
           try {
           Future<Integer> submit = pool.submit(new UserThread(id));
           results.add(submit);
           } catch (RejectedExecutionException ex) {
               misc++;
               continue;
           }
           threadsStarted++;
           id++;
       }
       pool.shutdownNow();

       int count = 0;
       for(Future<Integer> i : results) {
           try {
               switch(i.get()) {
                   case 0:
                       // Success
                       success++;
                       break;
                   case -1:
                       // Seat is not Reserved
                       seatNotReserved++;
                       break;
                   case -2:
                       // Seat is not Reserved by Customer ID
                       seatNotReservedByCustomerID++;
                       break;
                   case -3:
                       // Reservation Timeout
                       reservationTimeout++;
                       break;
                   case -4:
                       // Seat is occupied
                       seatIsOccupied++;
                       break;
                   default:
                       misc++;
                       // Everything else fails
                       break;
               }
           } catch (ExecutionException | InterruptedException ex) {
               misc++;
           }
           count++;
           System.out.println("Processed Future Objects: " + count);
           // HERE IS WHERE IT LOOPS
       }

你能发现这个问题吗?我在代码停止运行的地方添加了一条注释。

planeIsBooked
变为
true
时,您的planeIsBooked似乎永远不会在while循环中初始化为
true
。因此,请确保您的循环不是无限的。

第一件事是
,而(planeIsBooked==false)
总是计算为true,因为

planeIsBooked = false always , nowhere its initialized to true. 
那么,为什么while循环条件变为false并出现呢

设置内部while循环的某个位置
planeIsBooked=true
以从while循环中出来。

两件事:

首先,在调用
pool.shutdownNow()之后-您正在继续尝试立即获取结果。调用shutDownNow()没有阻塞,也不是池停止的明确指示。为此,您应该调用
pool.awaitTermination()

第二,不清楚你的评论是什么意思-

//这就是它循环的地方

这是在一个循环下——看看这个循环——如果在开关的情况下抛出了一个异常——那么它将进入catch——忽略它并循环。您是否检查了异常情况?

详细说明为什么您应该在多线程环境中将静态变量声明为volatile

尽管静态变量是易变的,但以下几行代码是危险的

while(planeIsBooked == false) {
        Future<Integer> submit = pool.submit(new UserThread(id));
   }
while(planeIsBooked==false){
Future submit=pool.submit(新用户线程(id));
}
考虑一下您预订的航班平均飞行时间为2秒。你们大概有300个座位(假设)。您的planeIsBooked字段将在600秒后变为true(如果它在单线程中运行)。有了50个大小的游泳池,它将在12秒内运行

根据上述假设,循环将运行12秒。 现在,想想submitrequest语句执行了多少次?我去过好几次。 即使你只有300个座位,你可能会在12秒内给appox更多的最少一百万个请求

因此,在调用Shutdown now()之前,请考虑队列中的作业数。这不是终止循环的正确方法


如果您知道航班座位的最大尺寸,为什么不在for-loop中使用它(可能是外部化for-loop中的参数,而不是变量来保持)

永远不要这样做:
planeIsBooked==false
planeIsBooked==(true==false)
可读性更强。或者
planeIsBooked==(1==2==true)
。你明白了。你为什么要关闭游泳池?我看你没有停止
线程t
。也可以使用中的工厂方法,而不是构造函数。@salyh您好,我是最初想提交问题的人,但我今天问得太多了。基本上我们关闭游泳池,因为我们现在实现了预订每个座位的目标n平面。此外,
planeIsBooked
不是
volatile
,因此如果您从其他线程更新它,此更改将不可见。基本上,此代码都是错误的…DBMonitor单独检查planeIsBooked,并将该变量刷新为true(有效)。您是否调试过以检查planeIsBooked设置false的值?因为在多线程环境中,为了使变量值在整个线程中保持一致,我们使用volatle,但您似乎没有这样做…因此它可能会向arraylist结果中添加无限值。请检查while循环是否正确运行?
while(planeIsBooked == false) {
        Future<Integer> submit = pool.submit(new UserThread(id));
   }