天天看點

LinkedBlockingQueue與ArrayBlockingQueue性能比較

實驗結論:在JDK1.8下,LinkedBlockingQueue性能優于ArrayBlockingQueue

實驗一:

public class BlockQueueApp {


    public static void main(String[] args) {

        //final LinkedBlockingQueue<Integer> queue = new LinkedBlockingQueue<Integer>(10000);
        final ArrayBlockingQueue<Integer> queue = new ArrayBlockingQueue<Integer>(10000);
        final Long start = System.currentTimeMillis();

        new Thread(new Runnable() {
            public void run() {
                for (int i = 0; i < 99999999; i++) {
                    try {
                        queue.put(i);
                    } catch (Exception e) {
                        e.printStackTrace();
                    }
                }
            }
        }).start();

        for (int j = 0; j < 10; j++) {
            new Thread(new Runnable() {
                public void run() {
                    try {
                        while (true) {
                            int i = queue.take();
                            if (i > 99999997) {
                                System.out.println(System.currentTimeMillis() - start);
                            }
                        }
                    } catch (Exception e) {
                        e.printStackTrace();
                    }
                }
            }).start();
        }

    }


}
           

實驗結果

Array ms

134471

93661

Linked ms

26919

25339

實驗二:

public class ArrayBlockingQueueVsLinkedBlockingQueue {
    //隊列最大容量
    public static final int Q_SIZE = 1024000;
    //生産者/消費者線程數
    public static final int THREAD_NUM = 4;

    //産品
    class Product {
        String name;

        Product(String name) {
            this.name = name;
        }
    }

    public void test(final BlockingQueue<Product> q) throws InterruptedException {
        //生産者線程
        class Producer implements Runnable {
            public void run() {
                for (int i = 0; i < Q_SIZE * 10; i++) {
                    try {
                        q.put(new Product("Lee"));
                    } catch (InterruptedException e) {
                        e.printStackTrace();
                    }
                }
            }

        }
        ;
        //消費者線程
        class Consumer implements Runnable {
            public void run() {
                for (int i = 0; i < Q_SIZE * 10; i++) {
                    try {
                        q.take();
                    } catch (InterruptedException e) {
                        // TODO Auto-generated catch block
                        e.printStackTrace();
                    }
                }
            }
        }
        ;
        //建立生産者
        Thread[] arrProducerThread = new Thread[THREAD_NUM];
        for (int i = 0; i < THREAD_NUM; i++) {
            arrProducerThread[i] = new Thread(new Producer());
        }
        //建立消費者
        Thread[] arrConsumerThread = new Thread[THREAD_NUM];
        for (int i = 0; i < THREAD_NUM; i++) {
            arrConsumerThread[i] = new Thread(new Consumer());
        }
        //go!
        long t1 = System.currentTimeMillis();
        for (int i = 0; i < THREAD_NUM; i++) {
            arrProducerThread[i].start();
            arrConsumerThread[i].start();
        }
        for (int i = 0; i < THREAD_NUM; i++) {
            arrProducerThread[i].join();
            arrConsumerThread[i].join();
        }
        long t2 = System.currentTimeMillis();
        System.out.println(q.getClass().getSimpleName() + " cost : " + (t2 - t1));
    }

    public static void main(String[] args) throws InterruptedException {
        final BlockingQueue<Product> q1 = new LinkedBlockingQueue<Product>(Q_SIZE);
        final BlockingQueue<Product> q2 = new ArrayBlockingQueue<Product>(Q_SIZE);
        new ArrayBlockingQueueVsLinkedBlockingQueue().test(q1);
        new ArrayBlockingQueueVsLinkedBlockingQueue().test(q2);
    }


}
           

實驗結果:

LinkedBlockingQueue cost : 10973

ArrayBlockingQueue cost : 13250

本文有部分實驗内容參考http://lazy2009.iteye.com/blog/1892559 ,但是結論與其相悖。