Skip to content

Instantly share code, notes, and snippets.

@iaveryanov
Created April 3, 2014 12:37
Show Gist options
  • Star 0 You must be signed in to star a gist
  • Fork 0 You must be signed in to fork a gist
  • Save iaveryanov/9953492 to your computer and use it in GitHub Desktop.
Save iaveryanov/9953492 to your computer and use it in GitHub Desktop.
How much idling?
package ru.inlinetelecom.vn2.util;
import java.util.concurrent.CountDownLatch;
import java.util.concurrent.ExecutorService;
import java.util.concurrent.Executors;
import java.util.concurrent.atomic.AtomicInteger;
import java.util.concurrent.atomic.AtomicLong;
/**
* вариант с uncontended lock (getAvailableProcessors >= worker_count
*/
public class AtomicCasTester {
// счетчик холостого хода
private static AtomicLong idlingCounter = new AtomicLong(0);
/**
* 1) вызывается из многих потоков
* 2) не должно быть меньше 0
* 3) если уже 0 и вызывают этот метод, то должно оставаться 0
*
* @param counter
* @return 0 or value after decrement
*/
private static int decUntilZero(AtomicInteger counter) {
while (true) {
int current = counter.get();
if (current == 0) {
return current;
}
int next = current - 1;
if (counter.compareAndSet(current, next)) {
return next;
}
idlingCounter.incrementAndGet();
}
}
public static void main(String[] args) throws InterruptedException {
final int initialValue = 400000000;
final int countOfThreads = 10; // всего потоков
final int countOfOperationsPerThread = initialValue/countOfThreads; // количество операций на один поток
final AtomicInteger counter = new AtomicInteger(initialValue);
ExecutorService executor = Executors.newFixedThreadPool(countOfThreads);
long startedAt = System.currentTimeMillis();
final CountDownLatch latch = new CountDownLatch(countOfThreads);
for (int i = 0; i < countOfThreads; i++) {
executor.execute(new Runnable() {
@Override
public void run() {
for (int i = 0; i < countOfOperationsPerThread; i++) {
decUntilZero(counter);
}
latch.countDown();
// System.out.println("task in progress..." + (latch.getCount()));
}
});
}
System.out.println("всех ждёмс, однако...");
latch.await();
long elapsed = System.currentTimeMillis() - startedAt;
executor.shutdown(); // за ненадобностью более!
System.out.println("Ну наконец-ТА дождалИСА!!! Урра товариСЧи, уРРа!");
printReport(initialValue, countOfThreads, countOfOperationsPerThread, counter, elapsed);
}
private static void printReport(int initialValue, int countOfThreads, int countOfOperationsPerThread, AtomicInteger counter, long elapsed) {
System.out.printf("================================================%n");
int current = counter.get();
int operations = initialValue - current;
System.out.printf("== INPUT DATA %n");
line("initial val", initialValue);
line("threads", countOfThreads);
line("operations/threads", countOfOperationsPerThread);
System.out.printf("== RESULTS %n");
lineWithPercent("current val", current, percent(current, initialValue));
lineWithPercent("operations", operations, percent(operations, initialValue));
lineWithPercent("idling", idlingCounter.get(), percent(idlingCounter.get(), initialValue));
line("elapsed(millis)", elapsed);
}
private static void line(String key, long value) {
System.out.printf("%-20s: %-10d %n", key, value);
}
private static void lineWithPercent(String key, long value, double percent) {
System.out.printf("%-20s: %-10d %.2f%% %n", key, value, percent);
}
private static float percent(float part, float total) {
return (part / total * 100);
}
private static float percent(long part, long total) {
return percent((float) part, (float) total);
}
}
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment