我找不到问题,有人能帮我吗。
public class Achterbahn {
private final Object monitor = new Object();
public synchronized void test() throws InterruptedException {
//monitor.wait();
System.out.println("car");
wait();
System.out.println("car");
}
public synchronized void Passagier() throws InterruptedException {
Thread.sleep(2000);
System.out.println("p");
notify();
//b.t1.notify();
}
public static void main(String []args) throws InterruptedException {
Thread t4 = new Thread(new Runnable() {
@Override
public void run() {
Achterbahn b = new Achterbahn();
try {
b.Passagier();
} catch (InterruptedException e) {
// TODO Auto-generated catch block
e.printStackTrace();
}
}
});
Thread t5= new Thread(new Runnable() {
@Override
public void run() {
Achterbahn b = new Achterbahn();
try {
b.test();
} catch (InterruptedException e) {
// TODO Auto-generated catch block
e.printStackTrace();
}
}
});
new Thread(t4).start();
new Thread(t5).start();
t5.join();
t4.join();
}
}
输出为:p车
它似乎是通知工作,我想打印也车在最后,但我不知道为什么它不工作
我希望有人能帮助我。尽快。
我在同一个类中有所有的方法,我也尝试过sepreate类,但是没有用
3条答案
按热度按时间2admgd591#
你做错了好几件事。
只启动c的一个示例。然后使用该示例调用您的方法。不同的示例在同步方法中不共享监视器
当你开始两个新的线程的时候。只需按如下方式启动它们:
主要问题是
t4
先开始,然后马上睡觉。所以呢t5
直到睡眠结束才开始。但到那时notify()
等待t4
在wait()
在中调用t5
因此wait
我永远也看不到。所以你需要付出t4
在睡觉前开始的机会。有几种方法可以解决这个问题。一种是使用一个标志来表示另一种方法已经就绪。但不要使用紧密的while循环。放一个sleep
在里面呆了一小段时间。我在下面举了一个例子。我还为线程分配了名称以匹配变量。xoefb8l82#
(我猜在这种情况下,“它没有工作”意味着程序挂起。请具体说明您看到的问题。)
有两个问题。一种是在每个线程中创建单独的对象。调用wait和notify的对象必须相同,等待的监视器是需要接收notify的监视器。在这段代码中,同步方法在调用方法的示例上使用内在锁。
在main方法中创建一次对象,每个线程需要引用同一个对象。
第二个问题,一旦你解决了第一个问题,将是一个竞赛条件。如果由一个线程执行的notify首先发生,那么当wait执行时,notify已经发生,并且wait将永远等待。
添加条件变量以记住是否发生了通知。
一般来说,模式是检查循环中的条件,请看这个问题:为什么我们必须使用“while”来检查竞争条件而不是“if”。post有一个使用变量查看是否发生了条件的示例,这里是
rfbsl7qr3#
这个代码对我有用我现在有了while循环