繁体   English   中英

在多线程中使用等待和通知方法

[英]Using wait and notify methods in MultiThreading

现在,我开始学习线程技术,并决定编写此类来演示多线程的思想,但是输出不是我想要的。

我写的课如下:-

import java.util.LinkedList;
class QueueTest extends LinkedList{
    int capacity;
    LinkedList list;
    public QueueTest(int capacity){
        this.capacity = capacity;
        list = new LinkedList();
    }
    public synchronized void addElements(int i)throws InterruptedException{
        if(list.size() == capacity ){
                wait();
        }
        add(i);
        System.out.println("I added : "+i);
        notify();
    }
    public synchronized int getElements() throws InterruptedException{
        if(!isEmpty()){
                wait();
        }
        int i = (Integer) list.remove();
        System.out.println("I got : "+i);
        notify();
        return i;
    }
}
class Add implements Runnable{
    QueueTest t ;
    public Add(QueueTest t){
        this.t = t;
        new Thread(this,"Add").start();
    }
    @Override
    public void run(){
        int i = 0;
        while(t.size() <= t.capacity){
            try{
                t.addElements(i++);} catch(InterruptedException e){}
        }
    }
}
class Remove implements Runnable{
    QueueTest t ;
    public Remove(QueueTest t){
        this.t = t;
        new Thread(this,"Remove").start();
    }
    @Override
    public void run(){
        while(!t.isEmpty()){
            try{
            t.getElements();} catch(InterruptedException e){}
        }
    }
}
public class FullQueue{
    public static void main(String[] args){
        QueueTest t = new QueueTest(5);
        new Add(t);
        new Remove(t);
    }
}

我期望输出是这样的

i added : 1
i got : 1
i added : 2
i got : 2 

...等等,但我得到了输出

I added : 0
I added : 1
I added : 2
I added : 3
I added : 4
I added : 5

由于这两个线程是同时运行的,因此根本无法保证或控制哪个线程何时或以什么顺序运行。

get可以在set之前完全运行,set可以首先完全运行,也可以混合运行。

像上面显示的那样均匀的交织是极不可能发生的。

在那种情况下,列表已被一个线程完全填充,但是空线程首先运行并在发现列表中没有内容时退出。

添加诊断程序以显示每个线程的开始和结束时间,您应该会看到。 结果会随每次运行而变化。

目前,您的notify无所作为,因为您没有任何等待。 要使线程交替,则在每次写或读之后,您应该通知然后等待。 但是,您将需要同步整个块,并且最终您将获得一种非常复杂的方法来获得与一个线程运行相同的结果。

这充满了比赛条件。 请注意,如果没有元素,则删除线程将立即退出。

暂无
暂无

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM