• Exchanger类详解


      Exchanger并发辅助类,允许在并发任务之间交换数据。具体来说Exchanger类在两个线程之间定义同步点。当两个线程到达同步点时,它们交换数据结构。需要注意的是Exchanger类只能同步两个线程。

      内存一致性效果:对于通过Exchanger成功交换对象的每对线程,每个线程中在exchanger()之前的操作 happen-before从另一线程中相应的exchanger()返回的后续操作。

    下面用一对一的生产者-消费者例子进行说明。

      生产者代码如下:

    public class Producer implements Runnable {
        private List<String> buffer;
        private Exchanger<List<String>> exchanger;
        public Producer(List<String> buffer, Exchanger<List<String>> exchanger) {
            this.buffer = buffer;
            this.exchanger = exchanger;
        }
        @Override
        public void run() {
            int cycle=1;
            for (int i=0; i<10; i++) {
                System.out.println("Producer:Cycle "+cycle);
                for (int j = 1; j <=10; j++) {
                    String msg="Event "+(i*10+j);
                    System.out.println("Producer: "+msg);
                    buffer.add(msg);
                }
                try {
                    buffer=exchanger.exchange(buffer);//和消费者交换数据结构
                } catch (InterruptedException e) {
                    e.printStackTrace();
                }
                System.out.println("Producer size: "+buffer.size());
                cycle++;
            }
        }
    
    }

      消费者代码:

    public class Consumer implements Runnable {
        private List<String> buffer;
        private Exchanger<List<String>> exchanger;
        public Consumer(List<String> buffer, Exchanger<List<String>> exchanger) {
            this.buffer = buffer;
            this.exchanger = exchanger;
        }
        @Override
        public void run() {
            int cycle=1;
            for (int i=0; i<=9; i++) {
                System.out.println("Consumer: Cycle "+cycle);
                try {
                    buffer=exchanger.exchange(buffer);//he生产者交换数据结构
                } catch (InterruptedException e) {
                    e.printStackTrace();
                }
                System.out.println("Consumer size: "+buffer.size());
                for (int j = 1; j <=10; j++) {
                    String msg=buffer.get(0);
                    System.out.println("Consumer: "+msg);
                    buffer.remove(0);
                }
                cycle++;
            }
        }
    }

      运行:

    public class Core {
        public static void main(String[] args) {
            List<String> buffer1=new ArrayList<String>();
            List<String> buffer2=new ArrayList<String>();
            Exchanger<List<String>> exchanger=new Exchanger<List<String>>();
            Producer producer=new Producer(buffer1, exchanger);
            Consumer consumer=new Consumer(buffer2, exchanger);
            Thread thread1=new Thread(producer);
            Thread thread2=new Thread(consumer);
            thread1.start();
            thread2.start();
        }
    }
  • 相关阅读:
    [翻译角]Headline English: A Captain Should Be Pitch Perfect at a Multitude of Skills (ESLPOD Blog)
    CF735D Taxes 哥德巴赫猜想判定素数 进一步猜想
    CF735C 数论平衡树叶子节点的最大深度贪心斐波那契条件归一化
    萌新的旅行&hdu5681单调队列的应用前缀和线段树ST表倍增解法
    CF731C Socks并查集(森林),连边,贪心,森林遍历方式,动态开点释放内存
    玲珑杯1007-A 八进制大数加法(实现逻辑陷阱与题目套路)
    关于石子合并
    codeforces724-B. Batch Sort
    codeforces724-A. Checking the Calendar 日期题
    如何筛选人
  • 原文地址:https://www.cnblogs.com/wxgblogs/p/5431249.html
Copyright © 2020-2023  润新知