Java wait और notify
In this page:
synchronized (lockObject) {
while (!condition) {
lockObject.wait();
}
lockObject.notify(); // or notifyAll()
}
Inter-Thread Communication
Inter-thread communication synchronized threads को Object class से inherited तीन methods का उपयोग करके अपना काम coordinate करने और signals exchange करने देता है: wait(), notify(), और notifyAll()। ये threads को loop में बेकार में poll करने के बजाय program में कहीं और conditions बदलने तक रुकने देते हैं।
उदाहरण: Inter-Thread Communication
// Define the class Main
public class Main {
// Program entry point: the JVM starts running here
public static void main(String[] args) throws InterruptedException {
// Create a new Object object and store it in monitor
Object monitor = new Object();
// synchronized lets only one thread run this code at a time
synchronized (monitor) {
// Print a line to the console
System.out.println("wait()/notify()/notifyAll() coordinate threads via this monitor");
}
}
}
Login to try C/C++/Java/PHP code in the editor
The wait() Method
किसी synchronized block के अंदर wait() call करना तुरंत calling thread को रोक देता है और, सबसे ज़रूरी बात, उस monitor lock को release कर देता है जो वह रखे हुए था, दूसरे threads को वही lock पाने और आगे बढ़ने देते हुए। waiting thread तब तक रुका रहता है जब तक कोई दूसरा thread उसी object पर notify() या notifyAll() call न करे।
उदाहरण: The wait() Method
public class Main {
public static void main(String[] args) throws InterruptedException {
final Object lock = new Object();
Thread waiter = new Thread(() -> {
synchronized (lock) {
try {
System.out.println("Waiting...");
lock.wait(200); // releases the lock while paused
System.out.println("Resumed");
} catch (InterruptedException e) {}
}
});
waiter.start();
waiter.join();
}
}
Login to try C/C++/Java/PHP code in the editor
The notify() Method
notify() method object के monitor lock का इंतज़ार कर रहे किसी एक, मनमाने ढंग से चुने गए thread को जगाता है। इसे उसी object पर किसी synchronized block के अंदर से call करना चाहिए, और अगर कई threads इंतज़ार कर रहे हों, तो कोई गारंटी नहीं कि कौन सा चुना जाएगा।
उदाहरण: The notify() Method
// Define the class Main
public class Main {
// Program entry point: the JVM starts running here
public static void main(String[] args) throws InterruptedException {
// Create a new Object object and store it in lock
final Object lock = new Object();
// Create a new Thread object and store it in waiter
Thread waiter = new Thread(() -> {
// synchronized lets only one thread run this code at a time
synchronized (lock) {
// Try code that might throw an exception
try { lock.wait(); } catch (InterruptedException e) {}
// Print a line to the console
System.out.println("Woken by notify()");
}
});
// Start the thread; it runs in parallel with this code
waiter.start();
Thread.sleep(100);
synchronized (lock) { lock.notify(); }
waiter.join();
}
}
Login to try C/C++/Java/PHP code in the editor
The notifyAll() Method
notifyAll() method सिर्फ एक के बजाय object के monitor का इंतज़ार कर रहे हर thread को जगाता है। जब कई threads अलग-अलग conditions के लिए इंतज़ार कर रहे हों तो यह आमतौर पर notify() से ज़्यादा सुरक्षित विकल्प है, क्योंकि notify() अकेले गलती से गलत वाले को जगा सकता है।
उदाहरण: The notifyAll() Method
public class Main {
public static void main(String[] args) throws InterruptedException {
final Object lock = new Object();
Runnable waitTask = () -> {
synchronized (lock) {
try { lock.wait(); } catch (InterruptedException e) {}
System.out.println(Thread.currentThread().getName() + " woken");
}
};
Thread t1 = new Thread(waitTask), t2 = new Thread(waitTask);
t1.start(); t2.start();
Thread.sleep(100);
synchronized (lock) { lock.notifyAll(); } // wakes both, not just one
t1.join(); t2.join();
}
}
Login to try C/C++/Java/PHP code in the editor
Producer-Consumer Simulation
Classic producer-consumer pattern किसी shared, bounded buffer को coordinate करने के लिए wait() और notify() का उपयोग करता है: producer तब wait() call करता है जब buffer भरा हो, और consumer तब wait() call करता है जब वह खाली हो, दोनों तरफ buffer की state बदलने के बाद दूसरे को जगाने के लिए notify() call करते हैं।
उदाहरण: Producer-Consumer Simulation
// Import java.util.LinkedList so it can be used by its short name
import java.util.LinkedList;
// Define the class Main
public class Main {
// Create a new LinkedList object and store it in buffer
static final LinkedList<Integer> buffer = new LinkedList<>();
static final int CAPACITY = 1;
// Program entry point: the JVM starts running here
public static void main(String[] args) throws InterruptedException {
// Create a new Thread object and store it in producer
Thread producer = new Thread(() -> {
// synchronized lets only one thread run this code at a time
synchronized (buffer) {
while (buffer.size() == CAPACITY) { try { buffer.wait(); } catch (InterruptedException e) {} }
buffer.add(42);
// Print a line to the console
System.out.println("Produced 42");
buffer.notify();
}
});
Thread consumer = new Thread(() -> {
// synchronized lets only one thread run this code at a time
synchronized (buffer) {
while (buffer.isEmpty()) { try { buffer.wait(); } catch (InterruptedException e) {} }
System.out.println("Consumed " + buffer.poll());
}
});
producer.start(); producer.join();
consumer.start(); consumer.join();
}
}
Login to try C/C++/Java/PHP code in the editor
- उसी object पर किसी
synchronizedblock के बाहरwait()याnotify()call करना, जोIllegalMonitorStateExceptionफेंकता है। wait()से पहले condition कोifसे जांचना बजायwhileloop के, जिससे एक spurious wakeup या कोई दूसरा thread condition को false छोड़ सकता है जब thread जारी रहता है।- दूसरे thread के
wait()call करने से पहलेnotify()call करना, जिससे signal खो जाता है और waiting thread हमेशा के लिए सोता रहता है।
Chapter Quiz — Complete all 8 topics to unlock
0/8 topics done
Complete these topics first: