Java LinkedBlockingQueue中的死锁(?)

Java LinkedBlockingQueue中的死锁(?),java,concurrency,queue,Java,Concurrency,Queue,我有一个非常基本的线程池代码。 它调用位于linkedblockingqueue中的工作对象池。 代码只是通过重新循环worker对象打印出输入数据 我发现与以下内容一致的死锁/冻结: public class throttleheapthreadpool{ private quoteworkerobject[] channels; private LinkedBlockingQueue<quoteworkerobject> idlec

我有一个非常基本的线程池代码。 它调用位于linkedblockingqueue中的工作对象池。 代码只是通过重新循环worker对象打印出输入数据

我发现与以下内容一致的死锁/冻结:

public class throttleheapthreadpool{
            private quoteworkerobject[] channels;
            private LinkedBlockingQueue<quoteworkerobject> idlechannels;
            public throttleheapthreadpool(int poolsize,int stocks){
        channels=new quoteworkerobject[poolsize];
        idlechannels=new LinkedBlockingQueue<quoteworkerobject>();

        for(int i=1;i<poolsize;i++){
            channels[i]=new quoteworkerobject(idlechannels);
            idlechannels.add(channels[i]);//All WORKERS to Idle pool to start
        }
    }

    public void execute(Integer quote){
        quoteworkerobject current = null;
        try {
                        //extract worker from pool
            current = (quoteworkerobject)idlechannels.take();
            current.put(quote);
        } catch (InterruptedException e) {
        }
    }

    class quoteworkerobject{
        LinkedBlockingQueue<Integer> taskqueue=new LinkedBlockingQueue<Integer>(); 
        Thread quotethread=null;
        LinkedBlockingQueue<quoteworkerobject> idle=null;
        @SuppressWarnings("unchecked")
        public quoteworkerobject(LinkedBlockingQueue<quoteworkerobject> idlechannels){
            this.idle=idlechannels;
            Runnable r=new Runnable(){
                public void run() {
                    insertquote();
                }
            };
            quotethread=new Thread(r);
            quotethread.start();//spawn a thread from the worker 
        }
        public void put(Integer  quote){
            taskqueue.add(quote);
        }
        public void insertquote(){
            try{
                Integer thisquote=taskqueue.take();
                idle.add(this);
            }
            catch(Exception ex){
            }

        }

    }

    public static void main(String[] args){
        throttleheapthreadpool pool=new throttleheapthreadpool(5,200);
        Random randomGenerator = new Random();

        for(int node=0;node < 20;node++){
            int d=randomGenerator.nextInt(5*200);
            pool.execute(d);
        }
    }

}   
公共类throttleheapthreadpool{
私人QuoteWorkrobject[]频道;
私有LinkedBlockingQueue idlechannels;
公共throttleheapthreadpool(int-poolsize,int-stocks){
通道=新的QuoteWorkRobject[poolsize];
idlechannels=newlinkedblockingqueue();
对于(int i=1;i请参见下面我的重构(仍然不完美,但可读性稍高)。您的问题如下:

  • 创建4个工作线程(在
    throttleheapthreadpool
    的构造函数中从1循环到5)
  • 每个辅助线程在单独的线程中运行一次
    insertquote
    ,然后返回空闲池
因此,总体而言,您提交4个已完成的作业,工人返回队列,然后再给他们额外的4个作业(总共8个),但他们不会使用该作业,因为他们的
insertquote
方法已退出

解决方案:在while循环中运行
insertquote

public void insertquote() {
    try {
        while (true) {
            taskqueue.take();
            idle.add(this);
        }
    } catch (Exception ex) {
    }
}
有关信息,请参阅我当前的代码版本:

public class ThrottleHeapThreadPool {

    private final BlockingQueue<QuoteWorkerObject> idlechannels = new LinkedBlockingQueue<QuoteWorkerObject>();

    public static void main(String[] args) {
        ThrottleHeapThreadPool pool = new ThrottleHeapThreadPool(5, 200);
        Random randomGenerator = new Random();

        for (int node = 0; node < 20; node++) {
            int d = randomGenerator.nextInt(5 * 200);
            pool.execute(d);
        }
    }

    public ThrottleHeapThreadPool(int poolsize, int stocks) {

        for (int i = 1; i < poolsize; i++) {
            QuoteWorkerObject worker = new QuoteWorkerObject(idlechannels);
            idlechannels.add(worker);//All WORKERS to Idle pool to start
            worker.init();
        }
    }

    public void execute(Integer quote) {
        try {
            //extract worker from pool
            QuoteWorkerObject worker = idlechannels.take();
            worker.put(quote);
        } catch (InterruptedException e) {
        }
    }

    class QuoteWorkerObject {

        private final BlockingQueue<Integer> taskqueue = new LinkedBlockingQueue<Integer>();
        private final BlockingQueue<QuoteWorkerObject> idle;

        @SuppressWarnings("unchecked")
        public QuoteWorkerObject(BlockingQueue<QuoteWorkerObject> idlechannels) {
            this.idle = idlechannels;
        }

        public void init() {
            new Thread(new Runnable() {
                public void run() {
                    insertquote();
                }
            }).start();
        }

        public void put(Integer quote) {
            taskqueue.add(quote);
        }

        public void insertquote() {
            try {
                while (true) {
                    taskqueue.take();
                    idle.add(this);
                }
            } catch (Exception ex) {
            }
        }
    }
}
公共类ThrottleHeapThreadPool{
private final BlockingQueue idlechannels=new LinkedBlockingQueue();
公共静态void main(字符串[]args){
ThrottleHeapThreadPool池=新的ThrottleHeapThreadPool(5200);
Random randomGenerator=新的Random();
用于(int node=0;node<20;node++){
int d=随机生成器.nextInt(5*200);
执行(d);
}
}
公共ThrottleHeapThreadPool(int-poolsize,int-stocks){
对于(int i=1;i
请参见下面我的重构(仍不完美,但可读性稍高)。您的问题如下:

  • 创建4个工作线程(在
    throttleheapthreadpool
    的构造函数中从1循环到5)
  • 每个辅助线程在单独的线程中运行一次
    insertquote
    ,然后返回空闲池
因此,总体而言,您提交4个已完成的作业,工人返回队列,然后再给他们额外的4个作业(总共8个),但他们不会使用该作业,因为他们的
insertquote
方法已退出

解决方案:在while循环中运行
insertquote

public void insertquote() {
    try {
        while (true) {
            taskqueue.take();
            idle.add(this);
        }
    } catch (Exception ex) {
    }
}
有关信息,请参阅我当前的代码版本:

public class ThrottleHeapThreadPool {

    private final BlockingQueue<QuoteWorkerObject> idlechannels = new LinkedBlockingQueue<QuoteWorkerObject>();

    public static void main(String[] args) {
        ThrottleHeapThreadPool pool = new ThrottleHeapThreadPool(5, 200);
        Random randomGenerator = new Random();

        for (int node = 0; node < 20; node++) {
            int d = randomGenerator.nextInt(5 * 200);
            pool.execute(d);
        }
    }

    public ThrottleHeapThreadPool(int poolsize, int stocks) {

        for (int i = 1; i < poolsize; i++) {
            QuoteWorkerObject worker = new QuoteWorkerObject(idlechannels);
            idlechannels.add(worker);//All WORKERS to Idle pool to start
            worker.init();
        }
    }

    public void execute(Integer quote) {
        try {
            //extract worker from pool
            QuoteWorkerObject worker = idlechannels.take();
            worker.put(quote);
        } catch (InterruptedException e) {
        }
    }

    class QuoteWorkerObject {

        private final BlockingQueue<Integer> taskqueue = new LinkedBlockingQueue<Integer>();
        private final BlockingQueue<QuoteWorkerObject> idle;

        @SuppressWarnings("unchecked")
        public QuoteWorkerObject(BlockingQueue<QuoteWorkerObject> idlechannels) {
            this.idle = idlechannels;
        }

        public void init() {
            new Thread(new Runnable() {
                public void run() {
                    insertquote();
                }
            }).start();
        }

        public void put(Integer quote) {
            taskqueue.add(quote);
        }

        public void insertquote() {
            try {
                while (true) {
                    taskqueue.take();
                    idle.add(this);
                }
            } catch (Exception ex) {
            }
        }
    }
}
公共类ThrottleHeapThreadPool{
private final BlockingQueue idlechannels=new LinkedBlockingQueue();
公共静态void main(字符串[]args){
ThrottleHeapThreadPool池=新的ThrottleHeapThreadPool(5200);
Random randomGenerator=新的Random();
用于(int node=0;node<20;node++){
int d=随机生成器.nextInt(5*200);
执行(d);
}
}
公共ThrottleHeapThreadPool(int-poolsize,int-stocks){
对于(int i=1;i