博客
关于我
强烈建议你试试无所不能的chatGPT,快点击我
Java Exchanger栅栏
阅读量:6412 次
发布时间:2019-06-23

本文共 3465 字,大约阅读时间需要 11 分钟。

hot3.png

1.含义

Exchanger是在两个任务之间交换对象的栅栏。当这些任务进入栅栏是,他们各自拥有一个对象,当他们离开时,他们都拥有之前由对象持有的对象。

2.使用场景

一个任务在创建对象,浙西对象的生产代价很高昂,而在另外一个任务在消费这些对象。通过这种方式,可以有更多的对象在被创建的同时被消费。

例子:

List做为生产端和消费端要交换的对象

对象生成器接口

public interface Generator
{ T next();}

对象初始化类

public class BasicGenerator
implements Generator
{ private Class
type; public BasicGenerator(Class
type) { this.type = type; } public T next() { try { return this.type.newInstance(); } catch (Exception var2) { throw new RuntimeException(var2); } } public static
Generator
create(Class
type) { return new BasicGenerator(type); }}

实体对象

public class Fat {    //保证线程可见性    private volatile  double d;    private static int counter = 0;    private final int id = counter++;    public Fat() {        for (int i = 0; i < 10000; i++) {            d += (Math.PI + Math.E) / (double)i;        }    }    public void operation() {        System.out.println(this);    }    public String toString() {        return "Fat id:" + id;    }}

生产端代码:

public class ExchangerProducer
implements Runnable{ private Exchanger
> exchanger; private Generator
generator; private List
holder; public ExchangerProducer(Exchanger
> exchanger, Generator
generator, List
holder) { this.exchanger = exchanger; this.generator = generator; this.holder = holder; } @Override public void run() { try { while (!Thread.interrupted()) { for (int i = 0; i < ExchangerDemo.size; i++) { T t = generator.next(); System.out.println("producer :" + t); holder.add(t);                    //生产端将list放入栅栏 holder = exchanger.exchange(holder); } } } catch (InterruptedException e) { e.printStackTrace(); } }}

消费端代码:

public class ExchangerConsumer
implements Runnable{ private Exchanger
> exchanger; private List
holder; private volatile T value; public ExchangerConsumer(Exchanger
> exchanger, List
holder) { this.exchanger = exchanger; this.holder = holder; } @Override public void run() { try { while(!Thread.interrupted()) {                //消费端获取栅栏中list holder = exchanger.exchange(holder);                //清除list中数据 for (T x : holder) { System.out.println("consumer :" + x); value = x; holder.remove(x); } } }catch (InterruptedException e) { System.err.println("OK to terminate this way."); } System.out.println("Final value:" + value); }}

测试代码:

public class ExchangerDemo {    static int size = 10;    static int delay = 1;    public static void main(String[] args) throws Exception{        if(args.length > 0) {            size = new Integer(args[0]);        }        if(args.length > 1) {            delay = new Integer(args[1]);        }        ExecutorService exec = Executors.newCachedThreadPool();        Exchanger
> xc = new Exchanger<>(); List
productList = new CopyOnWriteArrayList<>(); List
consumerList = new CopyOnWriteArrayList<>(); exec.execute(new ExchangerProducer
(xc, BasicGenerator.create(Fat.class), productList)); exec.execute(new ExchangerConsumer
(xc, consumerList)); TimeUnit.SECONDS.sleep(delay); exec.shutdownNow(); }}

转载于:https://my.oschina.net/u/1017791/blog/2967451

你可能感兴趣的文章
一、浅谈前端的2D、3D转换,以及动画的定义和调用(关于2D的一些操作)
查看>>
Python中关于++和—(自增和自减)的理解
查看>>
万物链、Ruff、沃尔顿链 物联网产品小结
查看>>
java常用jar包
查看>>
004-Java语言特点
查看>>
android 屏幕适配一:通过自定义View的方式实现适配
查看>>
学不好Python?我们分析看看正确的学习方法是什么-马哥教育
查看>>
面向对象复习日志二:Traits
查看>>
我的前端那些事--简介
查看>>
为什么在JavaScript中使用Prototype?[译]
查看>>
教妹学 Java:大有可为的集合
查看>>
微服务治理平台的RPC方案实现
查看>>
android 开发艺术view笔记
查看>>
程序员面试问答集锦,从容应对各种面试难题!
查看>>
你|可以为性感代言
查看>>
[仁润云技术团队]并发编程-(2)并发编程的目标
查看>>
Android 技术选型闲聊
查看>>
在 VS Code 中校验 Jenkinsfile
查看>>
数据结构与算法系列
查看>>
【直通BAT】剑指Offer 经典试题整理(4)
查看>>