g1101_1200.s1117_building_h2o.H2O Maven / Gradle / Ivy
Go to download
Show more of this group Show more artifacts with this name
Show all versions of leetcode-in-java21 Show documentation
Show all versions of leetcode-in-java21 Show documentation
Java-based LeetCode algorithm problem solutions, regularly updated
package g1101_1200.s1117_building_h2o;
// #Medium #Concurrency #2023_06_01_Time_19_ms_(89.19%)_Space_45.9_MB_(7.13%)
import java.util.concurrent.Semaphore;
/**
* 1117 - Building H2O\.
*
* Medium
*
* There are two kinds of threads: `oxygen` and `hydrogen`. Your goal is to group these threads to form water molecules.
*
* There is a barrier where each thread has to wait until a complete molecule can be formed. Hydrogen and oxygen threads will be given `releaseHydrogen` and `releaseOxygen` methods respectively, which will allow them to pass the barrier. These threads should pass the barrier in groups of three, and they must immediately bond with each other to form a water molecule. You must guarantee that all the threads from one molecule bond before any other threads from the next molecule do.
*
* In other words:
*
* * If an oxygen thread arrives at the barrier when no hydrogen threads are present, it must wait for two hydrogen threads.
* * If a hydrogen thread arrives at the barrier when no other threads are present, it must wait for an oxygen thread and another hydrogen thread.
*
* We do not have to worry about matching the threads up explicitly; the threads do not necessarily know which other threads they are paired up with. The key is that threads pass the barriers in complete sets; thus, if we examine the sequence of threads that bind and divide them into groups of three, each group should contain one oxygen and two hydrogen threads.
*
* Write synchronization code for oxygen and hydrogen molecules that enforces these constraints.
*
* **Example 1:**
*
* **Input:** water = "HOH"
*
* **Output:** "HHO"
*
* **Explanation:** "HOH" and "OHH" are also valid answers.
*
* **Example 2:**
*
* **Input:** water = "OOHHHH"
*
* **Output:** "HHOHHO"
*
* **Explanation:** "HOHHHO", "OHHHHO", "HHOHOH", "HOHHOH", "OHHHOH", "HHOOHH", "HOHOHH" and "OHHOHH" are also valid answers.
*
* **Constraints:**
*
* * `3 * n == water.length`
* * `1 <= n <= 20`
* * `water[i]` is either `'H'` or `'O'`.
* * There will be exactly `2 * n` `'H'` in `water`.
* * There will be exactly `n` `'O'` in `water`.
**/
@SuppressWarnings({"java:S106", "java:S2142"})
public class H2O {
private Semaphore hSemaphore;
private Semaphore oSemaphore;
public H2O() {
hSemaphore = new Semaphore(2);
oSemaphore = new Semaphore(2);
}
public void hydrogen(Runnable releaseHydrogen) throws InterruptedException {
hSemaphore.acquire();
// releaseHydrogen.run() outputs "H". Do not change or remove this line.
releaseHydrogen.run();
oSemaphore.release();
}
public void oxygen(Runnable releaseOxygen) throws InterruptedException {
oSemaphore.acquire(2);
// releaseOxygen.run() outputs "O". Do not change or remove this line.
releaseOxygen.run();
hSemaphore.release(2);
}
public static class HydrogenRunnable implements Runnable {
private H2O h2O;
public HydrogenRunnable(H2O h2O) {
this.h2O = h2O;
}
@Override
public void run() {
try {
h2O.hydrogen(() -> System.out.print('H'));
} catch (InterruptedException ignored) {
// ignored
}
}
}
public static class OxygenRunnable implements Runnable {
private H2O h2O;
public OxygenRunnable(H2O h2O) {
this.h2O = h2O;
}
@Override
public void run() {
try {
h2O.oxygen(() -> System.out.print('O'));
} catch (InterruptedException ignored) {
// ignored
}
}
}
}
© 2015 - 2025 Weber Informatics LLC | Privacy Policy