public class ProducerConsumer {
public static void main(String [] args) {
SyncStack ss = new SyncStack();
Producer p = new Producer(ss);
Consumer c = new Consumer(ss);
Thread p1 = new Thread(p);
Thread c1 = new Thread(c);
p1.start();c1.start();
while(c1.isAlive() == false) {
System.out.println("操作结束,一共进行了" +SyncStack.num + "次操作!");
}
}
}class Product {
private int id ;
Product(int id ) {
this.id = id;
}

public String toString() {
return "Product:" + id;
}
}class SyncStack {
private Product [] arr = new Product[10];
private int index = 0;
static int num = 0;

public synchronized void push(Product pd) {
while(index == arr.length) {
try {
this.wait();
}catch(InterruptedException x) {
x.printStackTrace();
}
}
this.notify();
num++;
arr[index] = pd;
index++;
}

public synchronized Product pop() {
while(index == 0) {
try {
this.wait();
}catch(InterruptedException x) {
x.printStackTrace();
}
}
this.notify();
num++;
index--;
return arr[index];
}

}class Producer implements Runnable {
private SyncStack ss;
Producer(SyncStack ss) {
this.ss = ss;
}

public void run() {
for(int i = 1;i<21;i++) {
Product pd = new Product(i);
ss.push(pd);
System.out.println("生产了" + pd + "!");
}
try {
Thread.sleep((int)(Math.random()*1000));
}catch(InterruptedException e) {
e.printStackTrace();
}
}
}class Consumer implements Runnable {
private SyncStack ss;
Consumer(SyncStack ss) {
this.ss = ss;
}

public void run() {
for(int i = 0;i<20;i++) {
Product pd = ss.pop();
System.out.println("消费了" + pd +"!");
try {
Thread.sleep((int)(Math.random()*1000));
}catch(InterruptedException e) {
e.printStackTrace();
}
}
}
}
这是一个关于生产者和消费者的小程序,但是运行结果与预期的不太一样。第一:生产和消费的顺序不是按照堆栈的形式打印出来;第二main方法最后的语句while(c1.isAlive() == false) {
System.out.println("操作结束,一共进行了" +SyncStack.num + "次操作!");
}
为什么执行不出来?
打印结果:
D:\java\ProducerConsumer>javac Pro**.javaD:\java\ProducerConsumer>java ProducerConsumer
生产了Product:1!
生产了Product:2!
生产了Product:3!
生产了Product:4!
生产了Product:5!
生产了Product:6!
生产了Product:7!
生产了Product:8!
消费了Product:3!
生产了Product:9!
生产了Product:10!
生产了Product:11!
生产了Product:12!
消费了Product:11!
生产了Product:13!
消费了Product:12!
生产了Product:14!
消费了Product:13!
生产了Product:15!
消费了Product:14!
生产了Product:16!
消费了Product:15!
生产了Product:17!
消费了Product:16!
生产了Product:18!
消费了Product:17!
生产了Product:19!
消费了Product:18!
生产了Product:20!
消费了Product:19!
消费了Product:20!
消费了Product:10!
消费了Product:9!
消费了Product:8!
消费了Product:7!
消费了Product:6!
消费了Product:5!
消费了Product:4!
消费了Product:2!
消费了Product:1!

解决方案 »

  1.   


    //你把这段换成下面一段就可以了
    while(c1.isAlive() == false) {
            System.out.println("操作结束,一共进行了" +SyncStack.num + "次操作!");
    }
    //换成这段
    while(c1.isAlive() == true) {
    }
    System.out.println("操作结束,一共进行了" +SyncStack.num + "次操作!");
    //或者换成这段
    try {
    Thread.currentThread().sleep(15000);
    } catch (InterruptedException e) {
    e.printStackTrace();
    }
    if(c1.isAlive() == false) {
    System.out.println("操作结束,一共进行了" +SyncStack.num + "次操作!");
    }
    //原来的while(c1.isAlive() == false)这句判断是在2个线程开始运行后就立即执行,while里面的条件又不成立,直接就过了,不会输出
      

  2.   

    我觉得你最后一句话说的不对,你想的我也考虑过, 可是那是while,条件不满足它会一直执行下去,是一个循环的状态,知道满足条件,就是没有满足的条件,也会是死循环的!
      

  3.   

    while条件满足它会一直执行下去
    while条件不满足它会直接跳出
    你原来执行while(c1.isAlive() == false)的时候,c1是活着的,所以c1.isAlive()为true,所以while条件不满足,直接跳出,
    下班,回家
      

  4.   

    所以要换成这段,
    条件满足(也就是c1线程活着)一直循环,
    条件不满足(也就是c1线程死了)跳出,执行输出
    while(c1.isAlive() == true) {
    }
    System.out.println("操作结束,一共进行了" +SyncStack.num + "次操作!");
      

  5.   

    哦,不好意思,刚刚理解错了,改成这样就能打印出操作的次数了,while(true) {
    if(c1.isAlive() == false) {
    System.out.println("操作结束,一共进行了" +SyncStack.num + "次操作!");
    return ;
    }

    }
    那第一个问题你能解决吗?关于堆栈的问题?
      

  6.   

    这样就对了。
    记得把打印信息也放到同步块中,否则打印和真正push/pop的时间点会不一致。public class ProducerConsumer {
    public static void main(String[] args) {
    SyncStack ss = new SyncStack();
    Producer p = new Producer(ss);
    Consumer c = new Consumer(ss);
    Thread p1 = new Thread(p);
    Thread c1 = new Thread(c);
    p1.start();
    c1.start();
    while (c1.isAlive() == true) {
    try {
    Thread.sleep(100);
    } catch (InterruptedException e) {}
    }
    System.out.println("操作结束,一共进行了" + SyncStack.num + "次操作!");
    }
    }class Product {
    private int id; Product(int id) {
    this.id = id;
    } public String toString() {
    return "Product:" + id;
    }
    }class SyncStack {
    private Product[] arr = new Product[10];
    private int index = 0;
    static int num = 0; public synchronized void push(Product pd) {
    while (index == arr.length) {
    try {
    this.wait();
    } catch (InterruptedException x) {
    x.printStackTrace();
    }
    }
    num++;
    arr[index] = pd;
    index++;
    System.out.println("生产了" + pd + "!");
    this.notify();
    } public synchronized Product pop() {
    while (index == 0) {
    try {
    this.wait();
    } catch (InterruptedException x) {
    x.printStackTrace();
    }
    }
    num++;
    index--;
    Product pd = arr[index];
    System.out.println("消费了" + pd + "!");
    this.notify();
    return pd;
    }}class Producer implements Runnable {
    private SyncStack ss; Producer(SyncStack ss) {
    this.ss = ss;
    } public void run() {
    for (int i = 1; i < 21; i++) {
    Product pd = new Product(i);
    ss.push(pd);
    }
    try {
    Thread.sleep((int) (Math.random() * 1000));
    } catch (InterruptedException e) {
    e.printStackTrace();
    }
    }
    }class Consumer implements Runnable {
    private SyncStack ss; Consumer(SyncStack ss) {
    this.ss = ss;
    } public void run() {
    for (int i = 0; i < 20; i++) {
    Product pd = ss.pop();
    try {
    Thread.sleep((int) (Math.random() * 1000));
    } catch (InterruptedException e) {
    e.printStackTrace();
    }
    }
    }
    }
      

  7.   


    //ls正解
    //这里的try要放到for (int i = 1; i < 21; i++)里面去吗
    class Producer implements Runnable {
        private SyncStack ss;    Producer(SyncStack ss) {
            this.ss = ss;
        }    public void run() {
            for (int i = 1; i < 21; i++) {
                Product pd = new Product(i);
                ss.push(pd);
            }
            try {
                Thread.sleep((int) (Math.random() * 1000));
            } catch (InterruptedException e) {
                e.printStackTrace();
            }
        }
    }
      

  8.   

    这个问题不需要说了,try是要放在for循环里面的,我开始给的程序有一个try没有放进去,所以消费和生产速度上相差很大,就像8楼说的那样没有随机性了,可是我想把一个生产者和一个消费者的问题变成多个消费者和多个生产者的问题,发现还是有些问题,就是那个id的控制上出了问题,大家看看能不能解决一下,这是我修改后的代码:public class ProducerConsumer {
    public static void main(String [] args) {
    SyncStack ss = new SyncStack();
    Producer pd1 = new Producer(ss,"生产者1");
    Producer pd2 = new Producer(ss,"生产者2");
    Producer pd3 = new Producer(ss,"生产者3");
    Consumer cs1 = new Consumer(ss,"消费者1");
    Consumer cs2 = new Consumer(ss,"消费者2");
    Consumer cs3 = new Consumer(ss,"消费者3");
    Thread p1 = new Thread(pd1);
    Thread p2 = new Thread(pd2);
    Thread p3 = new Thread(pd3);
    Thread c1 = new Thread(cs1);
    Thread c2 = new Thread(cs2);
    Thread c3 = new Thread(cs3);
    p1.start();c1.start();
    p2.start();c2.start();
    p3.start();c3.start();
    while(true) {
    if((c1.isAlive()||c2.isAlive()||c3.isAlive()) == false) {
    System.out.println("操作结束,一共进行了" +SyncStack.num + "次操作!");
    return ;
    }
    }
    }
    }class Product {
    private static int id =0 ;
    Product() {
    addId();
    }
    public synchronized void addId () {
    id++;
    }

    public String toString() {
    return "产品" + id;
    }
    }class SyncStack {
    private Product [] arr = new Product[10];
    private int index = 0;
    static int num = 0;

    public synchronized void push(Product pd) {
    while(index == arr.length) {
    try {
    this.wait();
    }catch(InterruptedException x) {
    x.printStackTrace();
    }
    }
    num++;
    arr[index] = pd;
    index++;
    this.notifyAll();
    }

    public synchronized Product pop() {
    while(index == 0) {
    try {
    this.wait();
    }catch(InterruptedException x) {
    x.printStackTrace();
    }
    }
    num++;
    index--;
    this.notifyAll();
    //System.out.println("index :" + index);
    return arr[index];
    }

    }class Producer implements Runnable {
    private SyncStack ss;
    private String name ;
    Producer(SyncStack ss,String s) {
    this.ss = ss;
    name = s;
    }

    public void run() {
    for(int i = 1;i<21;i++) {
    Product pd = new Product();
    //System.out.println(pd);
    ss.push(pd);
    System.out.println(name + "放进" + pd + "!");
    try {
    Thread.sleep((int)(Math.random()*1000));
    }catch(InterruptedException e) {
    e.printStackTrace();
    }
    }
    }
    }class Consumer implements Runnable {
    private SyncStack ss;
    private String name;
    Consumer(SyncStack ss,String s) {
    this.ss = ss;
    name = s;
    }

    public void run() {
    for(int i = 0;i<20;i++) {
    Product pd = ss.pop();
    //System.out.println(pd);
    System.out.println(name + "拿走" + pd +"!");
    try {
    Thread.sleep((int)(Math.random()*1000));
    }catch(InterruptedException e) {
    e.printStackTrace();
    }
    }
    }
    }
    运行结果会出现产品号id重复出现的情况!
      

  9.   

    楼主把id做成静态的了,各个对象是共享的。
    实际上要做两个,静态的用于计数,实例变量用于保存本对象的id,不能混用的。
      

  10.   

    我认为id作为产品的号码是独一无二的,不应该出现号码相同的产品,如果Id不是静态变量,那么在多个生产者和消费者的程序中,不同的生产者会生产出id(号码)相同的产品,这与现实是不符合的,所以我把id设置为静态的,而且每次生产一个产品后,Id就会加1,可是运行的时候还是有问题!
      

  11.   

    哦,我明白你的意思了,呵呵,我刚刚又理解错误了,不好意思啊,只要把Product类改成
    class Product {
    private static int count=0 ;
    private int id = 0;
    Product() {
    id = count+1;
    count++;
    }

    public String toString() {
    return "产品" + id;
    }
    }
    这样就没问题了,谢谢您的指导,非常感谢!
      

  12.   

    唉,可是我发现我的这个程序还是有些问题啊,我明明在程序中控制产品的放进和拿出是以堆栈的形式进行的,可是有时候还是会出现一些产品的放进和取出不是按照堆栈形式的小问题,而且我试验了很多次,发现sleep中的时间设置的越短,异常发生的概率越大,是不是CPU自身偶尔也会出现异常呢???比如说这是一部分运行情况:
    生产者3放进3 号产品!
    消费者3拿走3 号产品!
    消费者3拿走4 号产品!
    生产者1放进4 号产品!
    生产者3放进5 号产品!
    消费者1拿走5 号产品!
    生产者3放进6 号产品!
    消费者2拿走6 号产品!
    生产者2放进7 号产品!
    消费者3拿走7 号产品!这是我的代码:
    public class ProducerConsumer {
    public static void main(String [] args) {
    SyncStack ss = new SyncStack();
    Producer pd1 = new Producer(ss,"生产者1");
    Producer pd2 = new Producer(ss,"生产者2");
    Producer pd3 = new Producer(ss,"生产者3");
    Consumer cs1 = new Consumer(ss,"消费者1");
    Consumer cs2 = new Consumer(ss,"消费者2");
    Consumer cs3 = new Consumer(ss,"消费者3");
    Thread p1 = new Thread(pd1);
    Thread p2 = new Thread(pd2);
    Thread p3 = new Thread(pd3);
    Thread c1 = new Thread(cs1);
    Thread c2 = new Thread(cs2);
    Thread c3 = new Thread(cs3);
    p1.start();c1.start();
    p2.start();c2.start();
    p3.start();c3.start();
    while(true) {
    if((c1.isAlive()||c2.isAlive()||c3.isAlive()) == false) {
    System.out.println("操作结束,一共成产了" +Product.count + "件产品!");
    return ;
    }
    }
    }
    }class Product {
    static int count=0 ;
    private int id = 0;
    Product() {
    id = count+1;
    count++;
    }

    public String toString() {
    return id + " 号产品";
    }
    }class SyncStack {
    private Product [] arr = new Product[10];
    private int index = 0;

    public synchronized void push(Product pd) {
    while(index == arr.length) {
    try {
    this.wait();
    }catch(InterruptedException x) {
    x.printStackTrace();
    }
    }
    arr[index] = pd;
    index++;
    this.notifyAll();
    }

    public synchronized Product pop() {
    while(index == 0) {
    try {
    this.wait();
    }catch(InterruptedException x) {
    x.printStackTrace();
    }
    }
    index--;
    this.notifyAll();
    return arr[index];
    }

    }class Producer implements Runnable {
    private SyncStack ss;
    private String name ;
    Producer(SyncStack ss,String s) {
    this.ss = ss;
    name = s;
    }

    public void run() {
    for(int i = 1;i<21;i++) {
    Product pd = new Product();
    ss.push(pd);
    System.out.println(name + "放进" + pd + "!");
    try {
    Thread.sleep((int)(Math.random()*50));
    }catch(InterruptedException e) {
    e.printStackTrace();
    }
    }
    }
    }class Consumer implements Runnable {
    private SyncStack ss;
    private String name;
    Consumer(SyncStack ss,String s) {
    this.ss = ss;
    name = s;
    }

    public void run() {
    for(int i = 0;i<20;i++) {
    Product pd = ss.pop();
    System.out.println(name + "拿走" + pd +"!");
    try {
    Thread.sleep((int)(Math.random()*50));
    }catch(InterruptedException e) {
    e.printStackTrace();
    }
    }
    }
    }
      

  13.   

    public class ProducerConsumer {
    public static void main(String [] args) {
    SyncStack ss = new SyncStack();
    Producer pd1 = new Producer(ss,"生产者1");
    Producer pd2 = new Producer(ss,"生产者2");
    Producer pd3 = new Producer(ss,"生产者3");
    Consumer cs1 = new Consumer(ss,"消费者1");
    Consumer cs2 = new Consumer(ss,"消费者2");
    Consumer cs3 = new Consumer(ss,"消费者3");
    Thread p1 = new Thread(pd1);
    Thread p2 = new Thread(pd2);
    Thread p3 = new Thread(pd3);
    Thread c1 = new Thread(cs1);
    Thread c2 = new Thread(cs2);
    Thread c3 = new Thread(cs3);
    p1.start();c1.start();
    p2.start();c2.start();
    p3.start();c3.start();
    while(true) {
    if((c1.isAlive()||c2.isAlive()||c3.isAlive()) == false) {
    System.out.println("操作结束,一共成产了" +Product.count + "件产品!");
    return ;
    }
    }
    }
    }class Product {
    static int count=0 ;
    private int id = 0;
    Product() {
    id = count+1;
    count++;
    }

    public String toString() {
    return id + " 号产品";
    }
    }class SyncStack {
    private Product [] arr = new Product[10];
    private int index = 0;

    public synchronized void push(Product pd) {
    while(index == arr.length) {
    try {
    this.wait();
    }catch(InterruptedException x) {
    x.printStackTrace();
    }
    }
    arr[index] = pd;
    index++;
    this.notifyAll();
    }

    public synchronized Product pop() {
    while(index == 0) {
    try {
    this.wait();
    }catch(InterruptedException x) {
    x.printStackTrace();
    }
    }
    index--;
    this.notifyAll();
    return arr[index];
    }

    }class Producer implements Runnable {
    private SyncStack ss;
    private String name ;
    Producer(SyncStack ss,String s) {
    this.ss = ss;
    name = s;
    }

    public void run() {
    for(int i = 1;i<21;i++) {
    Product pd = new Product();
    ss.push(pd);
    System.out.println(name + "放进" + pd + "!");
    try {
    Thread.sleep((int)(Math.random()*50));
    }catch(InterruptedException e) {
    e.printStackTrace();
    }
    }
    }
    }class Consumer implements Runnable {
    private SyncStack ss;
    private String name;
    Consumer(SyncStack ss,String s) {
    this.ss = ss;
    name = s;
    }

    public void run() {
    for(int i = 0;i<20;i++) {
    Product pd = ss.pop();
    System.out.println(name + "拿走" + pd +"!");
    try {
    Thread.sleep((int)(Math.random()*50));
    }catch(InterruptedException e) {
    e.printStackTrace();
    }
    }
    }
    }
      

  14.   

    哦,6楼我说过了:
    记得把打印信息的System.out.println语句也放到push/pop同步块中,否则屏幕打印和真正push/pop的时间点会不一致。
      

  15.   

    修改好的代码:
    public class ProducerConsumer {
    public static void main(String [] args) {
    SyncStack ss = new SyncStack();
    Producer pd1 = new Producer(ss,"生产者1");
    Producer pd2 = new Producer(ss,"生产者2");
    Producer pd3 = new Producer(ss,"生产者3");
    Consumer cs1 = new Consumer(ss,"消费者1");
    Consumer cs2 = new Consumer(ss,"消费者2");
    Consumer cs3 = new Consumer(ss,"消费者3");
    Thread p1 = new Thread(pd1);
    Thread p2 = new Thread(pd2);
    Thread p3 = new Thread(pd3);
    Thread c1 = new Thread(cs1);
    Thread c2 = new Thread(cs2);
    Thread c3 = new Thread(cs3);
    p1.start();c1.start();
    p2.start();c2.start();
    p3.start();c3.start();
    while(true) {
    if((c1.isAlive()||c2.isAlive()||c3.isAlive()) == false) {
    System.out.println("操作结束,一共生产了" +Product.count + "件产品!");
    return ;
    }
    }
    }
    }class Product {
    static int count=0 ;
    private int id = 0;
    Product() {
    id = count+1;
    count++;
    }

    public String toString() {
    return id + " 号产品";
    }
    }class SyncStack {
    private Product [] arr = new Product[10];
    private int index = 0;

    public synchronized void push(Product pd ,String name) {
    while(index == arr.length) {
    try {
    this.wait();
    }catch(InterruptedException x) {
    x.printStackTrace();
    }
    }
    arr[index] = pd;
    System.out.println(name + "放进" + pd + "!");
    index++;
    this.notifyAll();
    }

    public synchronized Product pop(String name) {
    while(index == 0) {
    try {
    this.wait();
    }catch(InterruptedException x) {
    x.printStackTrace();
    }
    }
    index--;
    this.notifyAll();
    System.out.println(name + "拿走" + arr[index] +"!");
    return arr[index];
    }

    }class Producer implements Runnable {
    private SyncStack ss;
    private String name ;
    Producer(SyncStack ss,String s) {
    this.ss = ss;
    name = s;
    }

    public void run() {
    for(int i = 1;i<21;i++) {
    Product pd = new Product();
    ss.push(pd,name);
    try {
    Thread.sleep((int)(Math.random()*50));
    }catch(InterruptedException e) {
    e.printStackTrace();
    }
    }
    }
    }class Consumer implements Runnable {
    private SyncStack ss;
    private String name;
    Consumer(SyncStack ss,String s) {
    this.ss = ss;
    name = s;
    }

    public void run() {
    for(int i = 0;i<20;i++) {
    Product pd = ss.pop(name);
    try {
    Thread.sleep((int)(Math.random()*50));
    }catch(InterruptedException e) {
    e.printStackTrace();
    }
    }
    }
    }打印的结果:
    生产者1放进1 号产品!
    消费者3拿走1 号产品!
    生产者2放进3 号产品!
    消费者2拿走3 号产品!
    生产者3放进2 号产品!
    消费者1拿走2 号产品!
    生产者3放进4 号产品!
    生产者2放进5 号产品!
    消费者3拿走5 号产品!
    消费者2拿走4 号产品!
    生产者2放进6 号产品!
    消费者3拿走6 号产品!
    生产者2放进7 号产品!
    消费者2拿走7 号产品!
    生产者3放进9 号产品!
    生产者1放进8 号产品!
    消费者1拿走8 号产品!
    消费者3拿走9 号产品!
    生产者3放进10 号产品!
    消费者3拿走10 号产品!
    生产者1放进11 号产品!
    生产者2放进12 号产品!
    生产者3放进13 号产品!
    生产者3放进14 号产品!
    生产者3放进15 号产品!
    生产者2放进16 号产品!
    生产者1放进17 号产品!
    消费者3拿走17 号产品!
    生产者1放进18 号产品!
    生产者3放进19 号产品!
    生产者2放进20 号产品!
    消费者3拿走20 号产品!
    生产者1放进21 号产品!
    消费者2拿走21 号产品!
    消费者1拿走19 号产品!
    生产者3放进22 号产品!
    消费者2拿走22 号产品!
    消费者2拿走18 号产品!
    生产者2放进23 号产品!
    消费者3拿走23 号产品!
    生产者3放进24 号产品!
    消费者1拿走24 号产品!
    消费者2拿走16 号产品!
    生产者1放进25 号产品!
    消费者3拿走25 号产品!
    生产者2放进26 号产品!
    消费者3拿走26 号产品!
    消费者1拿走15 号产品!
    生产者3放进28 号产品!
    消费者2拿走28 号产品!
    生产者1放进27 号产品!
    生产者3放进30 号产品!
    消费者1拿走30 号产品!
    消费者3拿走27 号产品!
    消费者1拿走14 号产品!
    消费者2拿走13 号产品!
    生产者1放进31 号产品!
    消费者3拿走31 号产品!
    生产者2放进29 号产品!
    生产者3放进32 号产品!
    消费者2拿走32 号产品!
    消费者1拿走29 号产品!
    生产者2放进33 号产品!
    消费者3拿走33 号产品!
    生产者1放进34 号产品!
    消费者1拿走34 号产品!
    生产者2放进35 号产品!
    消费者1拿走35 号产品!
    生产者3放进36 号产品!
    消费者2拿走36 号产品!
    生产者3放进37 号产品!
    生产者1放进38 号产品!
    生产者2放进39 号产品!
    消费者3拿走39 号产品!
    消费者1拿走38 号产品!
    消费者2拿走37 号产品!
    生产者3放进40 号产品!
    生产者1放进41 号产品!
    消费者2拿走41 号产品!
    生产者1放进42 号产品!
    消费者3拿走42 号产品!
    生产者3放进44 号产品!
    消费者1拿走44 号产品!
    生产者2放进43 号产品!
    生产者1放进45 号产品!
    消费者2拿走45 号产品!
    消费者1拿走43 号产品!
    生产者1放进46 号产品!
    消费者3拿走46 号产品!
    生产者2放进47 号产品!
    生产者3放进48 号产品!
    消费者2拿走48 号产品!
    生产者2放进49 号产品!
    生产者3放进50 号产品!
    生产者2放进51 号产品!
    生产者1放进52 号产品!
    消费者3拿走52 号产品!
    消费者2拿走51 号产品!
    生产者3放进53 号产品!
    生产者2放进54 号产品!
    消费者2拿走54 号产品!
    生产者1放进55 号产品!
    消费者3拿走55 号产品!
    消费者1拿走53 号产品!
    消费者3拿走50 号产品!
    消费者1拿走49 号产品!
    生产者1放进56 号产品!
    消费者3拿走56 号产品!
    生产者2放进57 号产品!
    消费者2拿走57 号产品!
    消费者1拿走47 号产品!
    消费者1拿走40 号产品!
    消费者1拿走12 号产品!
    消费者2拿走11 号产品!
    生产者2放进58 号产品!
    消费者1拿走58 号产品!
    生产者1放进59 号产品!
    消费者2拿走59 号产品!
    生产者1放进60 号产品!
    消费者1拿走60 号产品!
    操作结束,一共生产了60件产品!还是有问题产生啊!!
      

  16.   

    这是我写的一个Product类实现,你参考下:class Product {
        static int count=0 ;
        private int id = 0;
        public synchronized static Product nextProduct(){
         Product p = new Product();
         count++;
         p.id = count;
         return p;
        }
        
        private Product() {
         super();
        }
        
        public String toString() {
            return id + " 号产品";
        }
    }把你19楼的Product类换下来就好了。