use*_*349 11 java concurrency multithreading
我有一个下面的方法,我想在以下条件下执行:
already executed或任何有用的东西返回.以下是我的方法:
public void initialize() {
List<Metadata> metadata = getMetadata(true);
List<Process> process = getProcess();
if (!metadata.isEmpty() && !process.isEmpty()) {
Manager.setAllMetadata(metadata, process);
}
startBackgroundThread();
}
Run Code Online (Sandbox Code Playgroud)
这可能吗?我正在使用Java 7.
Oli*_*ain 11
@ ShayHaned的解决方案使用锁定.您可以通过AtomicBoolean以下方式提高效率:
AtomicBoolean wasRun = new AtomicBoolean(false);
CountDownLatch initCompleteLatch = new CountDownLatch(1);
public void initialize() {
if (!wasRun.getAndSet(true)) {
List<Metadata> metadata = getMetadata(true);
List<Process> process = getProcess();
if (!metadata.isEmpty() && !process.isEmpty()) {
Manager.setAllMetadata(metadata, process);
}
startBackgroundThread();
initCompleteLatch.countDown();
} else {
log.info("Waiting to ensure initialize is done.");
initCompleteLatch.await();
log.warn("I was already run");
}
}
Run Code Online (Sandbox Code Playgroud)
以上假设您不必等待startBackgroundThread完成工作.如果您这样做,解决方案将变为:
AtomicBoolean wasRun = new AtomicBoolean(false);
CountDownLatch initCompleteLatch = new CountDownLatch(1);
public void initialize() {
if (!wasRun.getAndSet(true)) {
List<Metadata> metadata = getMetadata(true);
List<Process> process = getProcess();
if (!metadata.isEmpty() && !process.isEmpty()) {
Manager.setAllMetadata(metadata, process);
}
// Pass the latch to startBackgroundThread so it can
// call countDown on it when it's done.
startBackgroundThread(initCompleteLatch);
} else {
log.info("Waiting to ensure initialize is done.");
initCompleteLatch.await();
log.warn("I was already run");
}
}
Run Code Online (Sandbox Code Playgroud)
这样做的原因是AtomicBoolean.getAndSet(true),在一个原子操作中,将返回先前设置的值并使新值成为true.因此,false返回到您的方法的第一个线程将返回(因为该变量被初始化为false),并且它将原子地将其设置为true.由于第一个线程返回false,它将占用if语句中的第一个分支,并且您的初始化将会发生.任何其他调用都会发现自第一个线程将其设置为true后wasRun.getAndSet返回true,因此它们将获取第二个分支,您将获得所需的日志消息.
CountDownLatch初始化为1,因此除了第一次调用之外的所有线程await.它们将阻塞,直到第一个线程调用countDown,将计数设置为0,释放所有等待的线程.
| 归档时间: |
|
| 查看次数: |
3458 次 |
| 最近记录: |