public class NotifyAndWaitExample2 {
static int i = 0;
public static void main(String[] args) {
Thread t1 = new Thread(new Runnable() {
@Override
public void run() {
synchronized (this) {
if (i <= 0) {
System.out.println("i=" + i + "in t1");
System.out.println(Thread.currentThread().getName() + "is running");
try {
wait();
} catch (InterruptedException e) {
e.printStackTrace();
}
}
System.out.println(Thread.currentThread().getName() + "is waken up");
}
}
});
Thread t4 = new Thread(new Runnable() {
@Override
public void run() {
synchronized (this) {
i++;
System.out.println("i=" + i + "in t4");
System.out.println(Thread.currentThread().getName() + "is notifying");
try {
Thread.sleep(1000);
notify();
System.out.println("notified");
} catch (InterruptedException e1) {
// TODO Auto-generated catch block
e1.printStackTrace();
}
}
}
});
t1.start();
t4.start();
}
}
Here It is showing ouptut:-
i=0in t1
i=1in t4
Thread-0is running
Thread-1is notifying
notified
One last line should also be printed in output i.e; "Thread-0 is waken up
". Why after printing "notified" it doesn't loose lock to thread "t1 run() method " and continue with the code after wait() in t1 . i.e it should print "Thread-0 is waken up" after printing "notified".
Your synchronized
blocks have "no" effect.
Your synchronized(this)
just gets the lock for the Runnable
instance where you also implement the run
method.
Your Thread t1
will never be notified, it waits for the Runnable
where you use the wait()
method to get notified. The only object that holds a reference to this Runnable is the Thread
Object t1
and that will (usually) not call notify()
or notifyAll()
on that Runnable.
I'm using an int[]
for storing the int value as well as for holding the lock / monitor. The solution is only to show you how you could do it, not meant that this is good practice to do it this way.
I'd recommend to read a good tutorial about how synchronized in Java works.
I've modified you example so that it works as you expect.
public class NotifyAndWaitExample2 {
private static int[] i = {0};
public static void main(String[] args) {
Thread t1 = new Thread(new Runnable() {
@Override
public void run() {
synchronized (i) {
if (i[0] <= 0) {
System.out.println("i=" + i[0] + " in t1");
System.out.println(Thread.currentThread().getName() + " is running");
try {
i.wait();
} catch (InterruptedException e) {
e.printStackTrace();
}
}
System.out.println(Thread.currentThread().getName() + " is waken up");
}
}
});
Thread t4 = new Thread(new Runnable() {
@Override
public void run() {
synchronized (i) {
i[0]++;
System.out.println("i=" + i[0] + "in t4");
System.out.println(Thread.currentThread().getName() + " is notifying");
try {
Thread.sleep(1000);
i.notifyAll();
System.out.println("notifying");
} catch (InterruptedException e1) {
// TODO Auto-generated catch block
e1.printStackTrace();
}
}
}
});
t1.start();
t4.start();
}
}