在C#中等待回调安全吗?

在C#中等待回调安全吗?,c#,multithreading,C#,Multithreading,我有一个BeginRead,它在完成时调用ReadCallback函数。我想在回调中做的是等待缓冲区上的ManualResetEvent告诉我缓冲区是否为空,这样如果需要更多数据,我就可以发出新的BeginRead。我已经实现了这一点,它是有效的。但我的问题是:在回调中等待是否安全? 我是C#新手,如果这些是常规线程,我不会有任何疑问,但我不确定C#如何处理回调 谢谢。在我能想到的所有情况下,都会在线程池上调用APM回调 这将您的问题简化为“我可以阻止线程池线程吗?”。答案通常是肯定的,但也有缺

我有一个BeginRead,它在完成时调用ReadCallback函数。我想在回调中做的是等待缓冲区上的ManualResetEvent告诉我缓冲区是否为空,这样如果需要更多数据,我就可以发出新的BeginRead。我已经实现了这一点,它是有效的。但我的问题是:在回调中等待是否安全? 我是C#新手,如果这些是常规线程,我不会有任何疑问,但我不确定C#如何处理回调


谢谢。

在我能想到的所有情况下,都会在线程池上调用APM回调

这将您的问题简化为“我可以阻止线程池线程吗?”。答案通常是肯定的,但也有缺点

这样做是“安全的”,直到您耗尽池(然后您将面临死锁和极端吞吐量降低的风险,如>1000倍)

另一个缺点是通常阻塞线程的缺点。它们需要花费大量内存才能保存。大量线程可能导致大量上下文切换

你不能用wait吗?我想象您的代码如下所示:

while (true) {
 var readResult = await ReadAsync(...);
 await WaitForSomeConditionAsync(); //Instead of ManualResetEvent.
}
禁止阻塞。非常简单的代码。没有必要做任何特殊的事情来发布下一次阅读。它只是循环的一部分

我的工作模式类似于生产者/消费者


听起来是TPL数据流的一个很好的用途。数据流自动化了数据的转发、等待和限制。它完全支持异步。

如果回调是异步的,那么您可以自由地执行任何操作,因为它的名称更像这样:
Task.Run(callback)
。否则(若调用者使用回调结果)就是阻塞,但阻塞可能是安全的(若从线程内使用回调调用函数)。在这种情况下,等待应该是安全的。没有足够的信息来回答。什么是
BeginRead
方法
Socket.BeginRead
FileStream.BeginRead
?还是怎样谁向
手动重置事件发出信号?需要多长时间?etc@Sinatr不,在线程池线程中等待(长时间)是不安全的。如果有几次等待等待,那么您将强制线程池不必要地创建线程。是的,调用是异步的,我指的是NetworkStream.beginhead。当我使用的缓冲区变空时,ManualResetEvent由我自己设计的读取函数发出信号。我的工作模式类似于生产者/消费者。我使用BeginRead从流中获取数据,将数据放入缓冲区,当调用Read函数时,将数据从一个缓冲区移动到另一个缓冲区。