原先多线程并发编程的学习笔记和代码整理一下贴上来。
---------------------------------
线程协作与Condition接口
一、线程协作:
Java提供的线程之间协作方式主要有两种:
1、Object类中提供的wait、notify、notifyAll:
这种方式历史悠久,本篇只简单介绍一下。
相关知识点:
(1)wait()等待某个条件变化,这种条件将由另一个线程来改变,但不能因为测试这个条件而不断的空循环。所以wait()会在等待外部循环的时候挂起,并且只有在notify(),notifyAll()发生时,才会唤醒继续执行。
(2)必须从同步环境中调用wait()\notify()\notifyAll()。
在对象上调用wait()方法时,执行该代码的线程立即放弃它在对象上的锁。
当调用notify()时,并不意味着这时线程会放弃其锁,如果线程仍旧在完成同步代码,则线程在移出同步代码之前不会放弃锁,所以只调用notify()不意味着这时该锁将变得可用。
可以使用notifyAll()让所有线程冲出等待区,返回可运行状态。多个线程等待一个对象,使用notify()将只影响其中一个,具体哪个将由JVM决定。
(3)当使用wait()\notify()\notifyAll()时,几乎总有一个while(condition)循环包围着wait(),以便检查条件,并强制连续等待,直到条件满足为止。让时间到期,也可以令wait恢复执行,即使代码没有调用notify()或notifyAll()。因此,将wait()放入while循环,并且重新检查表示我们正在等待的事情的条件。我们确保不管因为什么原因醒来,当且仅当我们正在等待的事情还没有发生,将重新进入wait()。
2、javase5开始新加入的java.util.concurrent.locks包中Condition接口:
下面会重点介绍新接口的使用。
二、Condition接口:
javase5新加入的java.util.concurrent.locks包中提供了Condition接口,按照JDK文档的描述:
Condition将Object监视器方法(wait、notify和notifyAll)分解成截然不同的对象,以便通过将这些对象与任意Lock实现组合使用,为每个对象提供多个等待set(wait-set)。其中,Lock替代了synchronized方法和语句的使用,Condition替代了Object监视器方法的使用。
Condition实现可以提供不同于Object监视器方法的行为和语义,比如受保证的通知排序,或者在执行通知时不需要保持一个锁。
下面是一个示例:
这是一个给汽车涂蜡和抛光的例子,忘了当时是看了网上哪篇文章还是看了哪本书,觉得不错就记录下来了。
Condition使用起来与Object监视器方法比较类似,先定义一个汽车类:
class Car{ private boolean waxOn = false; private Lock lock = new ReentrantLock(); private Condition cond = lock.newCondition(); public void buffed(){ lock.lock(); try{ waxOn=false; cond.signalAll();// }finally{ lock.unlock(); } } public void waxed(){ lock.lock(); try{ waxOn=true; cond.signalAll();// }finally{ lock.unlock(); } } public void waitingForWax() throws InterruptedException{ lock.lock(); try{ while(waxOn==false){//汽车在抛光时一直等待 cond.await(); } }finally{ lock.unlock(); } } public void waitingForBuffing() throws InterruptedException{ lock.lock(); try{ while(waxOn==true){//汽车在涂蜡时一直等待 cond.await(); } }finally{ lock.unlock(); } } }
该类使用了ReentrantLock,并通过lock.newCondition();获取一个Condition。状态waxOn代表该车是否涂蜡,涂蜡之后抛光,因此waxed和buffed分别是涂蜡后和抛光后改变waxOn状态的操作。waitingForWax和waitingForBuffing代表等待涂蜡和等待抛光。
然后定义一个涂蜡任务:
class WaxOn implements Runnable{ private Car car; public WaxOn(Car c){ this.car=c; } @Override public void run() { try{ while(true){ System.out.println("waxOn!"); car.waxed(); car.waitingForBuffing(); } }catch(InterruptedException e){ e.printStackTrace(); } System.out.println("Ending WaxOn task."); } }这个任务一直循环给汽车涂蜡,不过每次涂蜡前要等汽车抛光完成之后再涂。
然后继续定义一个抛光任务:
class WaxOff implements Runnable{ private Car car; public WaxOff(Car c){ this.car=c; } @Override public void run(){ try{ while(true){ car.waitingForWax(); System.out.println("waxOff!"); car.buffed(); } }catch(InterruptedException e){ e.printStackTrace(); } System.out.println("Ending WaxOff task."); } }
该任务循环给汽车抛光,但抛光前需要先等涂蜡结束,然后再抛光。
最后,开始给汽车抛光和涂蜡了:
Car car=new Car(); ExecutorService es = Executors.newCachedThreadPool(); es.execute(new WaxOff(car)); es.execute(new WaxOn(car));
控制台输出:
waxOn! waxOff! waxOn! waxOff! waxOn! waxOff! ......
两个任务会循环不停的给汽车涂蜡和抛光,除非你手工停止这个程序。同时,涂蜡和抛光操作又不会同时进行,总是会等待另一个操作结束之后才开始,实现了2个线程的协作。
相关推荐
本资源致力于向您介绍 Java 并发编程中的线程基础,涵盖了多线程编程的核心概念、线程的创建和管理,以及线程间通信的基本方法。通过深入学习,您将建立扎实的多线程编程基础,能够更好地理解和应用多线程编程。 多...
Java并发编程:设计原则与模式(第二版).pdf
Java并发编程:设计原则与模式(第二版)
第二部分引入了ClassLoader,这是因为ClassLoader与线程不无关系,我们可以通过synchronized关键字,或者Lock等显式锁的方式在代码的编写阶段对共享资源进行数据一致性保护,那么一个Class在完成初始化的整个过程到...
Java线程:并发协作-生产者消费者模型 Java线程:并发协作-死锁 Java线程:volatile关键字 Java线程:新特征-线程池 Java线程:新特征-有返回值的线程 Java线程:新特征-锁(上) Java线程:新特征-锁(下) Java...
Java线程:并发协作-生产者消费者模型 Java线程:并发协作-死锁 Java线程:volatile关键字 Java线程:新特征-线程池 Java线程:新特征-有返回值的线程 Java线程:新特征-锁(上) Java线程:新特征-锁(下) ...
Java并发编程:设计原则与模式(第二版)
本文的主题是关于具有java语言风格的Thread、synchronized、volatile,以及J2SE5中新增的概念,如锁(Lock)、原子性(Atomics)、并发集合类、线程协作摘要、Executors。开发者通过这些基础的接口可以构建高并发、线程...
java并发编程:设计原则与模式.rar
同时,并发编程更广泛,它包括多线程编程,还包括其他并发技术和编程范式,以解决各种并发问题和场景。 总之,多线程是并发编程的一种具体实现方式,用于处理同一程序内的多个线程。而并发编程则更广泛,涵盖了处理...
高并发和并发编程并发编程:线程安全+线程封闭+线程调度
详细介绍java并发编程相关知识: 基础知识 并发与并行 Java并发演进历史 Java并发模型 线程模型 存储模型 JVM同步原语 volatile CAS 线程安全 保护“共享数据” 低级并发工具 原子变量 锁...
Java线程:概念与原理 2 一、操作系统中线程和进程的概念 2 ...Java线程:并发协作-线程的交互 47 Java线程:并发协作-生产者消费者模型 52 Java线程:并发协作-死锁 55 Java线程:线程之间的数据传递 58
Java并发编程:设计原则与模式Java并发编程:设计原则与模式
java线程与并发编程是java并发编程的盛典,绝对高清版
C++并发编程实战 示例源源码 (C++ Concurrency in Action)
Java线程:并发协作-生产者消费者模型 Java线程:并发协作-死锁 Java线程:volatile关键字 Java线程:新特征-线程池 Java线程:新特征-有返回值的线程 Java线程:新特征-锁(上) Java线程:新特征-锁(下) Java...
Java并发编程:volatile关键字解析