112 lines
3.3 KiB
Java
112 lines
3.3 KiB
Java
import org.junit.jupiter.api.RepeatedTest;
|
|
import org.junit.jupiter.api.Test;
|
|
import org.junit.jupiter.api.Timeout;
|
|
import ru.lionarius.sync.MyCountDownLatch;
|
|
|
|
import java.util.concurrent.TimeUnit;
|
|
import java.util.concurrent.atomic.AtomicBoolean;
|
|
|
|
import static org.junit.jupiter.api.Assertions.*;
|
|
|
|
class MyCountDownLatchTest {
|
|
@Test
|
|
void testInitialization() {
|
|
assertThrows(IllegalArgumentException.class, () -> new MyCountDownLatch(-1));
|
|
assertDoesNotThrow(() -> new MyCountDownLatch(0));
|
|
var latch = new MyCountDownLatch(5);
|
|
assertEquals(5, latch.getCount());
|
|
}
|
|
|
|
@Test
|
|
void testCountDown() {
|
|
var latch = new MyCountDownLatch(3);
|
|
assertEquals(3, latch.getCount());
|
|
latch.countDown();
|
|
assertEquals(2, latch.getCount());
|
|
latch.countDown();
|
|
assertEquals(1, latch.getCount());
|
|
latch.countDown();
|
|
assertEquals(0, latch.getCount());
|
|
latch.countDown();
|
|
assertEquals(0, latch.getCount());
|
|
}
|
|
|
|
@RepeatedTest(20)
|
|
void testAwait() throws InterruptedException {
|
|
var latch = new MyCountDownLatch(2);
|
|
var threadFinished = new AtomicBoolean(false);
|
|
|
|
var thread = new Thread(() -> {
|
|
try {
|
|
latch.await();
|
|
threadFinished.set(true);
|
|
} catch (InterruptedException ignored) {
|
|
}
|
|
});
|
|
|
|
thread.start();
|
|
Thread.sleep(100);
|
|
assertFalse(threadFinished.get());
|
|
|
|
latch.countDown();
|
|
Thread.sleep(100);
|
|
assertFalse(threadFinished.get());
|
|
|
|
latch.countDown();
|
|
thread.join(1000);
|
|
assertTrue(threadFinished.get());
|
|
}
|
|
|
|
@Test
|
|
@Timeout(value = 1000, unit = TimeUnit.MILLISECONDS)
|
|
void testMultipleThreads() throws InterruptedException {
|
|
final int THREAD_COUNT = 5;
|
|
var startLatch = new MyCountDownLatch(1);
|
|
var endLatch = new MyCountDownLatch(THREAD_COUNT);
|
|
AtomicBoolean[] threadsStarted = new AtomicBoolean[THREAD_COUNT];
|
|
AtomicBoolean[] threadsFinished = new AtomicBoolean[THREAD_COUNT];
|
|
|
|
for (int i = 0; i < THREAD_COUNT; i++) {
|
|
threadsStarted[i] = new AtomicBoolean(false);
|
|
threadsFinished[i] = new AtomicBoolean(false);
|
|
final int index = i;
|
|
new Thread(() -> {
|
|
try {
|
|
startLatch.await();
|
|
threadsStarted[index].set(true);
|
|
Thread.sleep(100);
|
|
threadsFinished[index].set(true);
|
|
endLatch.countDown();
|
|
} catch (InterruptedException ignored) {
|
|
}
|
|
}).start();
|
|
}
|
|
|
|
Thread.sleep(100);
|
|
for (var started : threadsStarted) {
|
|
assertFalse(started.get());
|
|
}
|
|
|
|
startLatch.countDown();
|
|
Thread.sleep(50);
|
|
|
|
for (var started : threadsStarted) {
|
|
assertTrue(started.get());
|
|
}
|
|
|
|
endLatch.await();
|
|
for (var finished : threadsFinished) {
|
|
assertTrue(finished.get());
|
|
}
|
|
assertEquals(0, endLatch.getCount());
|
|
}
|
|
|
|
@Test
|
|
@Timeout(value = 1000, unit = TimeUnit.MILLISECONDS)
|
|
void testZeroCount() throws InterruptedException {
|
|
var latch = new MyCountDownLatch(0);
|
|
assertEquals(0, latch.getCount());
|
|
assertTrue(latch.tryAwait());
|
|
}
|
|
}
|