0

我正在尝试wait(),以及notify()多线程的方法。

我想出了一个小项目,我试图用多线程来解决。我有一辆出租车,可以达到 6 级,我有一个乘客可以达到 6 级。

出租车将更早到达 Rank 6,乘客和wait()乘客。当Passenger达到Rank6时,他会notify()

接到通知后,那辆出租车将继续循环,不会进入其他等级。

出租车.java

package multhithreading.engage.hireForHier;

public class Taxi implements Runnable {

Rank rank = null;

public Taxi(Rank rank) {
    this.rank = rank;
}

public void run() {
    System.out.println(Thread.currentThread().getName() + "  Destined for rank No. " + rank.getRankNo());
    synchronized (rank) {

        for (int i = 1; i < 10; i++) {
            System.out.println("Taxi has reached rank: " + i);
            if (i == 6) {
                try {
                    rank.wait();
                } catch (InterruptedException e) {
                    e.printStackTrace();
                }// catch
            }// if

            try {
                Thread.sleep(100);
            } catch (InterruptedException e) {
                e.printStackTrace();
            }// catch

        }// for
    }// synchronized

}// run

}

乘客.java

package multhithreading.engage.hireForHier;

public class Passenger implements Runnable {

Rank rank = null;

public Passenger(Rank rank) {
    this.rank = rank;
}

public void run() {
    System.out.println(Thread.currentThread().getName() + "  Destined for rank No. " + rank.getRankNo());

    synchronized (rank) {

        for (int i = 1; i < 10; i++) {

            System.out.println("Passenger has reached rank: " + i);
            if (i == 6) {
                notify();

            }// if
            try {
                Thread.sleep(180);
            } catch (InterruptedException e) {
                e.printStackTrace();
            }// catch

        }// for
    }// synchronized

}// run
}

Rank.java

package multhithreading.engage.hireForHier;


public class Rank {

private int rankNo = 0;

public Rank(int rankNo) {
    this.rankNo = rankNo;
}

public int getRankNo() {
    return rankNo;
}
}

TaxiHire.java

package multhithreading.engage.hireForHier;

public class TaxiHire {

public static void main(String[] args) {

    Rank rank6 = new Rank(6);

    Taxi taxiNo3 = new Taxi(rank6);
    Passenger passengerNo3 = new Passenger(rank6);

    Thread taxi_thread = new Thread(taxiNo3, "taxi_thread");

    Thread passenger_thread = new Thread(passengerNo3, "passenger_thread");

    taxi_thread.start();
    passenger_thread.start();
}

}

我得到的输出是:

taxi_thread  Destined for rank No. 6
Taxi has reached rank: 1
passenger_thread  Destined for rank No. 6
Taxi has reached rank: 2
Taxi has reached rank: 3
Taxi has reached rank: 4
Taxi has reached rank: 5
Taxi has reached rank: 6
Passenger has reached rank: 1
Passenger has reached rank: 2
Passenger has reached rank: 3
Passenger has reached rank: 4
Passenger has reached rank: 5
Passenger has reached rank: 6
Exception in thread "passenger_thread" java.lang.IllegalMonitorStateException
    at java.lang.Object.notify(Native Method)
    at lesson9.engage.hireForHier.Passenger.run(Passenger.java:20)
    at java.lang.Thread.run(Unknown Source)

我需要知道为什么抛出异常,对我来说,Taxi 线程似乎没有取回锁。这个场景应该如何实现,Taxi线程如何继续循环。

您的帮助将不胜感激。

4

2 回答 2

1

错误在乘客类中,您同步 rand 对象但通知该对象,因此您的代码是

if (i == 6) {
                notify();

            }// if

并且应该是

if (i == 6) {
                try{rank.notify();
                }catch(Exception ex){/*When no any thread is waiting for rank object.*/}

            }// if

出租车线程也有可能先行,所以在这里你也会遇到异常,因为没有任何线程在等待排名对象。

所以先启动打车线程,再启动乘客,最可靠的方法是用打车线程调用乘客线程。它确保您的出租车线程先行。

链接可能会帮助您解决可能的情况。

于 2013-10-17T08:31:33.133 回答
1
if (i == 6) {
   notify();

在这里您没有调用rank.notify(),因此默认行为将尝试在对象(对象)上调用通知this,这将在您不锁定时Passenger抛出IllegalMonitorStateExceptionthis

IllegalMonitorStateException当您尝试wait()notify()notifyAll() 在对象上而不锁定该对象时发生。

解决方案:

if (i == 6) {
   rank.notify();
于 2013-10-17T08:32:13.497 回答