java - AsynchronousByteChannel 的线程含义

标签 java multithreading asynchronous nio completionhandler

AsynchronousByteChannel.read() 的 Javadoc说操作是异步发生的,但是当到达流的末尾时会发生什么?是否允许实现在调用 read() 的同一线程中触发完成处理程序?从实现的角度来看,没有理由异步执行此操作,因为我们已经知道结果。同样,如果用户试图读入一个 ByteBuffer,其中 remaining() 返回 0,我们知道读取操作必须返回 0。

我问是因为我在自己的 AsynchronousByteChannel 实现中遇到了竞争条件。我正在调用一个完成处理程序,该处理程序在操作完成时对自身调用 notify() 。然后我调用以下用户代码:

CompletionHandler<?, ?> handler = ...;
synchronized (handler)
{
  asyncByteChannel.read(handler);
  handler.wait();
}

请注意,用户假设操作完成时会通知处理程序,但因为 read() 实际上是同步调用完成处理程序,所以它会在 wait() 之前得到通知,而后者将永远阻塞。

规范是否要求我在单独的线程中更新 CompletionHandler,或者用户是否应该意识到调用 read() 的线程可能会同步执行某些操作?

最佳答案

即使在另一个线程上调用处理程序,也不能保证它会在 read 方法返回后调用,即在您的 wait() 之后调用 开始。 (好吧,同步锁似乎可以保证这一点。)

您应该使用同步和 boolean 变量来等待和锁定:

CompletionHandler<?, ?> handler = ...;
synchronized (handler)
{
   asyncByteChannel.read(handler);
   while(!handler.finished) {
     handler.wait();
   }
}

... 然后您的处理程序会将 finished 变量设置为 true。

关于java - AsynchronousByteChannel 的线程含义,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/6666659/

相关文章:

java - Apache curator InterProcessSemaphoreMutex 版本是否会挂起?

java - 如何从java中的两个数组中删除重复的字符串?

java - 破译某些文本的最有效方法

ios - 从并行窗口显示 View Controller (具有相同的父级)

Python:在第一个函数保持运行的同时运行第二个函数

c++ - 混合松弛和释放-获取内存指令

Haskell:启动一个长时间运行的进程,默默地捕获标准输出

c# - asyncawait的实际例子不符合预期

c# - 等到单元测试中的所有任务完成

java - 两个字符串 - 哪个更好?