多线程之六:并发设计模式

什么是设计模式

    在软件工程中,设计模式(design pattern)是对软件设计中普遍存在(反复出现)的各种问题 ,所提出的解决方案

    架构模式 – MVC – 分层

    设计模式提炼系统中的组件

    代码模式(成例 Idiom

        – 低层次,与编码直接相关

        – DCL

不变模式

    一个类的内部状态创建后,在整个生命期间都不会发生变化时,就是不变类

    不变模式不需要同

    代码示例:

public final class Product {
	//确保无子类
	private final String no;
	//私有属性,不会被其他对象获取
	private final String name;
	//final保证属性不会被2次赋值
	private final double price;
	//在创建对象时,必须指定数据
	public Product(String no, String name, double price) { 
		super();
		//因为创建之后,无法进行修改
		this.no = no;
		this.name = name;
		this.price = price;
	}
	public String getNo() {
		return no;
	}
	public String getName() {
		return name;
	}
	public double getPrice() {
		return price;
	}
}

        JDK中的不变类:

            java.lang.String

            java.lang.Boolean

            java.lang.Byte

            java.lang.Character

            java.lang.Double

            java.lang.Float

            java.lang.Integer

            java.lang.Long

            java.lang.Short

 

        Future模式

        核心思想

            异步调

            主线程可以获取到目标线程的处理结果

        与join()的区别

            join():主线程需要阻塞直到目标线程执行结束

            Future:启动了目标线程之后主线程还可以继续其他操作,直到需要取目标线程的处理结果的时候才进行等待。

主要构造:

        代码示例:

public interface Data {
 public String getResult ();
}
public class FutureData implements Data {
 protected RealData realdata = null; //FutureData是RealData的包装
 protected boolean isReady = false;
 public synchronized void setRealData(RealData realdata) {
	 if (isReady) {
		return;
	 }
	 this.realdata = realdata;
	 isReady = true;
	 notifyAll(); //RealData已经被注入,通知getResult()
 }
 public synchronized String getResult() { //会等待RealData构造完成
	 while (!isReady) {
		 try {
			wait(); //一直等待,知道RealData被注入
		 } catch (InterruptedException e) {
		 }
	 }
	return realdata.result; //由RealData实现
 }
}

public class RealData implements Data {
 protected final String result;
 public RealData(String para) {
	 //RealData的构造可能很慢,需要用户等待很久,这里使用sleep模拟
	 StringBuffer sb=new StringBuffer();
	 for (int i = 0; i < 10; i++) {
		 sb.append(para);
		 try {
			//这里使用sleep,代替一个很慢的操作过程
			Thread.sleep(100);
		 } catch (InterruptedException e) {
		 }
	}
	result =sb.toString();
 }
 public String getResult() {
	 return result;
 }
}
public class Client {
 public Data request(final String queryStr) {
	final FutureData future = new FutureData();
	new Thread() {
		public void run() {// RealData的构建很慢,
			//所以在单独的线程中进行
			RealData realdata = new RealData(queryStr);
			future.setRealData(realdata);
		}
	}.start();
	return future; // FutureData会被立即返回
 }
}
public static void main(String[] args) {
 Client client = new Client();
 //这里会立即返回,因为得到的是FutureData而不是RealData
 Data data = client.request("name");
 System.out.println("请求完毕");
 try {
	 //这里可以用一个sleep代替了对其他业务逻辑的处理
	 //在处理这些业务逻辑的过程中,RealData被创建,从而充分利用了等待时间
	 Thread.sleep(2000);
 } catch (InterruptedException e) {
 }
 //使用真实的数据,数据如果没准备好,这里会进行阻塞
 System.out.println("数据 = " + data.getResult());
}

        JDKFuture模式的支

        

            代码示例:

public class RealData implements Callable<String> {
	private String para;
	public RealData(String para){
		this.para=para;
	}
	@Override
	public String call() throws Exception {
		StringBuffer sb=new StringBuffer();
		for (int i = 0; i < 10; i++) {
			sb.append(para);
			try {
				Thread.sleep(100);
			} catch (InterruptedException e) {
			}
		}
		return sb.toString();
	}
}
	public class FutureMain {
	public static void main(String[] args) throws InterruptedException, ExecutionException {
		//构造FutureTask
		FutureTask<String> future = new FutureTask<String>(new RealData("a"));
		ExecutorService executor = Executors.newFixedThreadPool(1);
		//执行FutureTask,相当于上例中的 client.request("a") 发送请求
		//在这里开启线程进行RealData的call()执行
		executor.submit(future);

		System.out.println("请求完毕");
		try {
			//这里依然可以做额外的数据操作,这里使用sleep代替其他业务逻辑的处理
			Thread.sleep(2000);
		} catch (InterruptedException e) {
		}
		//相当于data.getResult (),取得call()方法的返回值
		//如果此时call()方法没有执行完成,则依然会等待
		System.out.println("数据 = " + future.get());
	}
}
public class FutureMain2 {
 public static void main(String[] args) throws InterruptedException, ExecutionException {

	 ExecutorService executor = Executors.newFixedThreadPool(1);
	 //执行FutureTask,相当于上例中的 client.request("a") 发送请求
	 //在这里开启线程进行RealData的call()执行
	 Future<String> future=executor.submit(new RealData("a"));
	 System.out.println("请求完毕");
	 try {
		 //这里依然可以做额外的数据操作,这里使用sleep代替其他业务逻辑的处理
		 Thread.sleep(2000);
	 } catch (InterruptedException e) {
	 }
	 //相当于data.getResult (),取得call()方法的返回值
	 //如果此时call()方法没有执行完成,则依然会等待
	 System.out.println("数据 = " + future.get());
 }
}

生产者消费

    生产者-消费者模式是一个经典的多线程设计模式。它为多线程间的协作提供了良好的解决方案。 在生产者-消费者模式中,通常由两类线程,即若干个生产者线程和若干个消费者线程。生产者线 程负责提交用户请求,消费者线程则负责具体处理生产者提交的任务。生产者和消费者之间则通 过共享内存缓冲区进行通信

    主要角色:

    

    类图:

     

  • 0
    点赞
  • 1
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值