Last active
February 18, 2024 17:04
-
-
Save sshark/7d29a51e44d550cbb5f0c920744d21a1 to your computer and use it in GitHub Desktop.
Controlled threads execution
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
package th.lim; | |
import java.util.concurrent.ExecutorService; | |
import java.util.concurrent.Executors; | |
/** | |
* Suppose we have the following code: | |
* | |
* class Foo { | |
* void first() {...} | |
* void second() {...} | |
* void third() {...} | |
* } | |
* | |
* The same instance of Foo will be passed to three different threads. Thread | |
* A will call first(), Thread B will call second(), and Thread C will call | |
* third(). Design a mechanism to ensure that first() is called before | |
* second() and second() is called before third(). | |
*/ | |
public class Foo { | |
Object lock = new Object(); | |
int action = 1; | |
void first() { | |
synchronized (lock) { | |
System.out.println(Thread.currentThread().getName() + " -> first"); | |
action++; | |
// must be notifyAll() instead of notify(). Otherwise, it might hang if | |
// task t3 gets notified instead | |
lock.notifyAll(); | |
} | |
} | |
void second() { | |
synchronized (lock) { | |
while (action != 2) { | |
try { | |
lock.wait(); | |
} catch (Exception e) { | |
} | |
} | |
System.out.println(Thread.currentThread().getName() + " -> second"); | |
action++; | |
lock.notify(); // notify is sufficient because there is only 1 thread waiting | |
} | |
} | |
void third() { | |
synchronized (lock) { | |
while (action != 3) { | |
try { | |
lock.wait(); | |
} catch (Exception e) { | |
} | |
} | |
System.out.println(Thread.currentThread().getName() + " -> third"); | |
} | |
} | |
public static void main(String[] args) { | |
Foo foo = new Foo(); | |
Runnable t1 = foo::first; | |
Runnable t2 = foo::second; | |
Runnable t3 = foo::third; | |
ExecutorService es = Executors.newCachedThreadPool(); | |
es.submit(t3); | |
es.submit(t2); | |
es.submit(t1); | |
es.shutdown(); | |
} | |
} |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment