关于线程之间的通信问题:
以下俩版本代码均采用“生产-消费模式”模拟生产与消费包子的过程,区别在于资源加锁和通信的位置,目前还不知道为啥错了/痛哭/痛哭:
(解决方法已更新)
先看失败版本:
package mycode;
public class Cotest {
public static void main(String[] args) {
Container con = new Container();
new Provider(con).start();
new Customer(con).start();
}
}
//生产者
class Provider extends Thread{
Container con;
public Provider(Container con) {
super();
this.con = con;
}
public void run() {
for (int i = 1; i <= 100; i++) {
//管道已满 ,失败
synchronized (con) {
if(con.len == con.buns.length) {
try {
this.wait();
} catch (InterruptedException e) {
System.out.println("生产者抛出异常");
}
}
Steamedbun bun = new Steamedbun(i);
System.out.println("生产-->第"+bun.id+"个包子");
con.push(bun);
this.notifyAll();
}
}
}
}
//消费者
class Customer extends Thread{
Container con;
public Customer(Container con) {
super();
this.con = con;
}
public void run() {
for (int i = 1; i <= 100; i++) {
//管道已空,失败
synchronized (con) {
if (con.len == 0) {
try {
this.wait();
} catch (InterruptedException e) {
System.out.println("消费者抛出异常");
}
}
Steamedbun bun = con.pop();
System.out.println("消费-->第"+bun.id+"个包子");
this.notifyAll();
}
}
}
}
//管道容器
class Container{
int len = 0; //容器内包子的数量
Steamedbun[] buns = new Steamedbun[10];
//生产包子
public void push(Steamedbun bun) {
buns[len]=bun;
len++;
}
//消费包子
public Steamedbun pop() {
len--;
return buns[len];
}
}
//包子
class Steamedbun{
int id;
public Steamedbun(int id) {
super();
this.id = id;
}
}
再看成功版本
package reference;
public class Cotest02 {
public static void main(String[] args) {
Container con = new Container();
new Provider(con).start();
new Customer(con).start();
}
}
//生产者
class Provider extends Thread{
Container con;
public Provider(Container con) {
super();
this.con = con;
}
public void run() {
for (int i = 1; i <= 100; i++) {
Steamedbun bun = new Steamedbun(i);
System.out.println("生产-->第"+bun.id+"个包子");
con.push(bun);
}
}
}
//消费者
class Customer extends Thread{
Container con;
public Customer(Container con) {
super();
this.con = con;
}
public void run() {
for (int i = 1; i <= 100; i++) {
//管道已空,失败
Steamedbun bun = con.pop();
System.out.println("消费-->第"+bun.id+"个包子");
}
}
}
//管道容器
class Container{
int len = 0;//容器内包子的数量
Steamedbun[] buns = new Steamedbun[10];
//生产包子
public synchronized void push(Steamedbun bun) {
//管道已满 ,失败
if(len == buns.length) {
try {
this.wait();
} catch (InterruptedException e) {
System.out.println("生产者抛出异常");
}
}
buns[len]=bun;
len++;
this.notifyAll();
}
//消费包子
public synchronized Steamedbun pop() {
if (len == 0) {
try {
this.wait();
} catch (InterruptedException e) {
System.out.println("消费者抛出异常");
}
}
len--;
Steamedbun bun = buns[len] ;
this.notifyAll();
return bun;
}
}
//包子
class Steamedbun{
int id;
public Steamedbun(int id) {
super();
this.id = id;
}
}