.net 将TcpClient WriteAsync和ReadAsync包装到MailboxProcessor中值得吗? 问题摘要: Stream.WriteAsync和Stream.ReadAsync是否没有相互阻塞,并且可以在2个cpu内核上完全并行运行 在异步{}中是否有通知等待外部源通知的方法 MailboxProcessor作为TcpClient的包装对性能有什么影响 一些解释:
正如我从Stream.cs异步操作的源代码中了解到的,异步操作是同步完成的,而不是完全并行完成的(如果您读取某些内容,它会阻止其他读取尝试,直到完成为止,并且还会阻止写入尝试,以其他方式相同-写入块读取和写入尝试),唯一的好处是它不会阻塞调用writeAsync/readAsync的线程 因此,我将TcpClient包装到MailboxProcessor中,它接受.net 将TcpClient WriteAsync和ReadAsync包装到MailboxProcessor中值得吗? 问题摘要: Stream.WriteAsync和Stream.ReadAsync是否没有相互阻塞,并且可以在2个cpu内核上完全并行运行 在异步{}中是否有通知等待外部源通知的方法 MailboxProcessor作为TcpClient的包装对性能有什么影响 一些解释:,.net,f#,asyncsocket,mailboxprocessor,.net,F#,Asyncsocket,Mailboxprocessor,正如我从Stream.cs异步操作的源代码中了解到的,异步操作是同步完成的,而不是完全并行完成的(如果您读取某些内容,它会阻止其他读取尝试,直到完成为止,并且还会阻止写入尝试,以其他方式相同-写入块读取和写入尝试),唯一的好处是它不会阻塞调用writeAsync/readAsync的线程 因此,我将TcpClient包装到MailboxProcessor中,它接受 键入AgentRequest读取响应a读取正确的响应: 第1步: 写请求 阅读应答a 第2步: 写入请求B 阅读响应B 队列:[“写
键入AgentRequest读取响应a
读取正确的响应:
第1步:
写请求
阅读应答a
第2步:
写入请求B
阅读响应B
队列:[“写入请求A”;“写入请求B”;“读取响应B”;“读取响应A”]
这将导致responseA返回到thread2,responseB返回到thread1
好消息是请求-响应由请求中设置的id关联。
因此,有一些用于此协议的解决方案存储字典
。这样就可以等待任务完成(TaskCompletionSource set result),然后继续执行结果。结果集由单独的单个线程设置,该线程保持从tcp流读取响应并按id映射它们
在F#中,使用异步而不是任务非常漂亮,因此我看到如何将响应映射到正确的请求的方法是存储字典单元>
或者,对于MailboxProcessor,我只能有一条消息,比如发送请求
,并且不能将写请求和读响应分开
除了异步之外,还有其他类似于TaskCompletionSource的方法吗,因此我可以:
//而不是
异步的{
做!发送请求
sharedDictionary.Add(request.id,fun resp->()(*处理此响应*)
read()}
//做点像
异步的{
做!发送请求
let!response=read request.id
(*用这个响应做点什么*)}
Stream
的基本实现基于向后兼容的原因进行同步多路复用:原始的Stream
接口仅为同步接口,这意味着不需要覆盖读
和写
来支持异步。但是,流的专门实现,特别是NetworkStream
和SslStream
,重写ReadAsync
和WriteAsync
,并通过委托给底层套接字来实现,因此,实现了真正的异步和非阻塞通信。流
的基本实现实现了这种同步复用,原因是向后兼容:原始的流
接口仅是同步的,这意味着不需要重写读取
和写入
来支持异步。然而,流的专门实现,特别是NetworkStream
和SslStream
,重写ReadAsync
和WriteAsync
,并通过委托给底层套接字来实现,从而实现真正的异步和无阻塞通信。