java - 理解 CompletableFuture 简单实现

标签 java multithreading completable-future

考虑以下摘自 this article 的代码.出于学习目的,它实现了类似于 CompletableFuture 的东西。

这是 WaitingFutureget() 函数:

@Override
public V get() throws ExecutionException {
    this.thread = Thread.currentThread();
    LockSupport.park(this);

    if (throwable != null) {
        throw new ExecutionException(throwable);
    }

    return result;
}

下面是 RunnableWaitingFuturerun() 函数:

@Override
    public void run() {
            try {
                waitingFuture.result = userFunction.get();
            } catch (Throwable throwable) {
                waitingFuture.throwable = throwable;
            } finally {
                waitingFuture.finished = true;
                LockSupport.unpark(waitingFuture.thread);
            }
        }
    }

问题:
在我看来,如果 run() 将在 get() 被调用之前完成,那么 LockSupport.park(this); 将被调用 LockSupport.unpark(waitingFuture.thread) 之后,让线程永远停止。

这是真的吗?

最佳答案

park()/unpark() 不同于wait/notify,因为信号不会'如果在 park() 之前调用了 unpark,则不会丢失。

但是,仍然只有一个位没有计算 unpark 被调用的频率,因此假设所有调用都将完美配对仍然是错误的。

此外,park 将在中断时静默返回,甚至可以虚假地返回,这意味着没有任何理由。

换句话说,即使从 park() 返回也不能保证条件已经满足。就像其他通知机制一样,无法在循环中使用它。

引用的代码更糟,因为它有另一个关于 thread 变量的竞争条件。不能保证它已在另一个线程读取它以通知它的时候写入。

关于java - 理解 CompletableFuture 简单实现,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/63452789/

相关文章:

java - 如果没有按预期工作

java - 如何判断字符串中的某个字符是否为大写

.net - 无论如何要知道池线程(或 ThreadStatic 成员)何时被销毁?

c++ - 在 For 循环 C++ 中创建线程

java - CompletableFuture 链接结果

java - 在 catch block 内抛出异常 - 它会再次被捕获吗?

java - 需要解析 LinkedList 下存在的 JSON 对象并计算字段值

c++ - 信号和槽的混淆行为取决于连接类型

java - Mono 与 CompletableFuture

multithreading - CompletableFuture 重用池中的线程