我在令人困惑的应用程序中遇到一些奇怪的行为。线程池可以重用一个标准线程吗?
我创建了一个线程,我们称它为worker,它负责处理通信请求。当线程使用请求并发送消息时,客户端在管道上写入数据。现在
,该线程的主循环有这样的事情:
lock(this)
{
object_id = Transport.BeginSend(xxx, xxx, callback, yyy)
clientsObjects[object_id] = client_id;
}
现在回调需要访问CLIENT_ID(它有点超过我写的复杂,但事情是回调接收OBJECT_ID,只是假设BeginSend是UdpClient.BeginSend
通话
void Callback(IAsyncResult ar)
{
State st = (State)ar;
lock(this)
{
client_id = clientsObjects[st.object_id]
}
}
锁是因为有回调可能会触发如此之快,它实际上发生之前clientsObjects[object_id] = client_id;
可以执行...
好的,现在..问题是它不能正常工作,它现在工作,然后......为什么?如果我跟踪正在执行BeginSend的线程的ManagedThreadIds和正在执行回调的线程,我发现有时它们具有相同的ThreadId!
这可能吗?这怎么可能发生?任何关于我在做什么错误的建议?
评论:实际的代码并不完全像这样,Transport是UDPClient的一个包装,它允许轻松改变传输层,锁不是真正的锁,但是自旋锁......但是这个概念本身或多或少是我的已经写下来了。
令人惊讶的是,确实有时异步调用变为同步...什么是混乱! – 2009-02-26 15:10:03