ConcurrentLinkedQueue并发容器

这是一个买票的问题

public class TicketSeller2 {
    static Vector<String> tickets = new Vector<>(); 
    static {
        for (int i = 0; i < 1000; i++) {
            tickets.add("票-" + i);
        }
    }
    public static void main(String[] args) {
        for (int i = 0; i < 10; i++) {
            new Thread(() -> {
          //这里的size()和remove()都是原子性的,但问题会出现在size()和remove()之间
while (tickets.size() > 0) { // 展现代码问题方法,将线程沉睡一会
            //当代吗醒来时,会有可能大量的高并发去争夺最后一张票,从而导致问题
try { TimeUnit.SECONDS.sleep(1); } catch (InterruptedException e) { e.printStackTrace(); } System.out.println("销售了:" + tickets.remove(0)); } }).start(); } } }

解决方案:

public class TicketSeller3 {

    static List<String> tickets = new ArrayList<>();

    static {
        for (int i = 0; i < 1000; i++) {
            tickets.add("票-" + i);
        }
    }

    public static void main(String[] args) {
        for (int i = 0; i < 10; i++) {
            new Thread(() -> {
                while (tickets.size() > 0) {
                    // sychronized 保证了原子性
                    synchronized (tickets) {
                        System.out.println("销售了:" + tickets.remove(0));
                    }
                }
            }).start();
        }
    }
}

3.优化

public class TicketSeller4 {
    static Queue<String> queue = new ConcurrentLinkedQueue<>();
    static {
        for (int i = 0; i < 1000; i++) {
            queue.add("票-" + i);
        }
    }
    public static void main(String[] args) {
        for (int i = 0; i < 10; i++) {
            new Thread(() -> {
                while (true) {
                    String t = queue.poll(); // 取出头,拿不到就是空值
                    if (t == null) {
                        break;
                    }
                    System.out.println("销售了:" + t);
                }
            }).start();
        }
    }
}
原文地址:https://www.cnblogs.com/gxlaqj/p/11699079.html