浅谈-----多线程(四)
来源:互联网 发布:ots工程师知乎 编辑:程序博客网 时间:2024/04/29 17:51
经典案例---生产者与消费者
大概情形:生产者不断生产,消费者不断取走生产者生产的产品。
大致如下:
存在问题:
①数据完整性问题。假设生产者线程刚向数据存储空间添加了信息的名称,还没有加入该信息的内容,程序就切换到了消费者线程,消费者线程把信息的名称和上一个信息的内容联系在一起。
②重复取和重复设置的问题。生产者放了若干次的数据,消费者才开始取数据,或者是消费者取完一个数据后,还没等生产者放入新的数据,又重复取出已取过的数据。
程序基本实现:
Info.java
class Info {private String name = "李兴华";private String content = "JAVA讲师";public String getName() {return name;}public void setName(String name) {this.name = name;}public String getContent() {return content;}public void setContent(String content) {this.content = content;}}
Producer.java
public class Producer implements Runnable {private Info info = null;public Producer(Info info) {// TODO Auto-generated constructor stubthis.info = info;}@Overridepublic void run() {// TODO Auto-generated method stubboolean flag = false;for (int i = 0; i < 50; i++) {if(flag) {this.info.setName("李兴华");try {Thread.sleep(90);} catch (InterruptedException e) {// TODO Auto-generated catch blocke.printStackTrace();}this.info.setContent("JAVA讲师");flag = false;} else {this.info.setName("mldn");try {Thread.sleep(90);} catch (InterruptedException e) {// TODO Auto-generated catch blocke.printStackTrace();}this.info.setContent("www.mldnjava.cn");flag = true;}}}}
Consumer.java
public class Consumer implements Runnable {private Info info = null;public Consumer(Info info) {// TODO Auto-generated constructor stubthis.info = info;}@Overridepublic void run() {// TODO Auto-generated method stubfor (int i = 0; i < 50; i++) {try {Thread.sleep(100);} catch (InterruptedException e) {// TODO Auto-generated catch blocke.printStackTrace();}System.out.println(this.info.getName() + "-->"+ this.info.getContent());}}}
测试:
public class ThreadCaseDemo01 {/** * @param args */public static void main(String[] args) {// TODO Auto-generated method stubInfo i = new Info();Producer pro = new Producer(i);Consumer con = new Consumer(i);new Thread(pro).start();new Thread(con).start();}}
得到:
问题出现了,怎么解决呢?
先来解决数据的完整性问题,在Info类中设置同步方法即可。
Info.java
class Info {private String name = "李兴华";private String content = "JAVA讲师";public String getName() {return name;}public void setName(String name) {this.name = name;}public String getContent() {return content;}public void setContent(String content) {this.content = content;}public synchronized void set(String name, String content) {this.setName(name);try {Thread.sleep(300);} catch (InterruptedException e) {// TODO Auto-generated catch blocke.printStackTrace();}this.setContent(content);}public synchronized void get() {try {Thread.sleep(300);} catch (InterruptedException e) {// TODO Auto-generated catch blocke.printStackTrace();}System.out.println(this.getName() + "-->" + this.getContent());}}
运行结果:
数据完整得到了解决,但是还是没解决重复取和重复设置问题。
这时,可以通过Object类对线程的支持来进行实现。
再次修改Info类,得到:
class Info {private String name = "李兴华";private String content = "JAVA讲师";private boolean flag = false;public String getName() {return name;}public void setName(String name) {this.name = name;}public String getContent() {return content;}public void setContent(String content) {this.content = content;}public synchronized void set(String name, String content) {if(!flag) {try {super.wait();} catch (InterruptedException e) {// TODO Auto-generated catch blocke.printStackTrace();}}this.setName(name);try {Thread.sleep(300);} catch (InterruptedException e) {// TODO Auto-generated catch blocke.printStackTrace();}this.setContent(content);flag = false;super.notify();}public synchronized void get() {if(flag) {try {super.wait();} catch (InterruptedException e) {// TODO Auto-generated catch blocke.printStackTrace();}}try {Thread.sleep(300);} catch (InterruptedException e) {// TODO Auto-generated catch blocke.printStackTrace();}System.out.println(this.getName() + "-->" + this.getContent());flag = true;super.notify();}}
运行得到:
整个问题得到解决。
0 0
- 浅谈-----多线程(四)
- Java多线程编程(四)—浅谈synchronized与lock
- Java多线程编程(四)—浅谈synchronized与lock
- Java多线程编程(四)—浅谈synchronized与lock
- Java多线程编程(四)—浅谈synchronized与lock
- [多线程之旅]四、浅谈volatile
- 浅谈-----多线程(一)
- 浅谈-----多线程(二)
- 浅谈-----多线程(三)
- 浅谈-----多线程(五)
- 浅谈SVM(四)
- 浅谈Git(四)
- 浅谈.NET下的多线程和并行计算(四)线程同步基础下 (转)
- 浅谈简约四策略(四)
- C#多线程浅谈(存档)
- 浅谈C++容器(四)
- 浅谈C++容器(四)
- 浅谈自考学习方法(四)
- PHP包管理工具-Composer的用法
- KD-Tree
- UVa 11223 - O: dah dah dah!
- 《The Swift Programming Language》中文版(全本翻译已完结).html
- linux中fork()函数详解
- 浅谈-----多线程(四)
- wireshark过滤规则
- ELK日志收集系统调研(四) -- 入门学习资源索引
- 千年传承古方
- SEL和IMP
- 大数据分析流程
- ABAP delete的用法
- 经纬财富:邵阳现货白银新手入门
- cocos2dx 以子弹飞行为例讲解拖尾效果类CCMotionStreak