C# 为什么IOCP不';不要在BeginExecuteReader中工作

C# 为什么IOCP不';不要在BeginExecuteReader中工作,c#,asynchronous,iocp,C#,Asynchronous,Iocp,我读过很多文章说IOCP用于BeginXX/EndXX对调用。 然而,当我测试它们时,我的结果显示IOCP在BeginExecuteReader调用中不起作用,而在BeginGetResponse调用中却工作得很好 我对这个结果感到非常困惑。谁能告诉我原因吗?我的测试代码有什么问题吗 以下是测试: 使用BeginGetResponse进行测试 代码: 结果: Begin:5;3; id = 10 End:5;2; id = 13 Begin:5;3; id = 10 End:4;3; id =

我读过很多文章说IOCP用于BeginXX/EndXX对调用。 然而,当我测试它们时,我的结果显示IOCP在BeginExecuteReader调用中不起作用,而在BeginGetResponse调用中却工作得很好

我对这个结果感到非常困惑。谁能告诉我原因吗?我的测试代码有什么问题吗

以下是测试:

  • 使用BeginGetResponse进行测试

    代码:

    结果:

    Begin:5;3; id = 10
    End:5;2; id = 13
    
    Begin:5;3; id = 10
    End:4;3; id = 7
    
    一个IO线程用于执行回调

  • 使用BeginExecuteReader进行测试 代码:

    结果:

    Begin:5;3; id = 10
    End:5;2; id = 13
    
    Begin:5;3; id = 10
    End:4;3; id = 7
    
    另一个工作线程用于执行回调


  • 有什么问题吗?

    你的复制很有创意。这是一个有趣的案例

    尝试使用命令文本“waitfordelay'02:00';”启动100个SqlCommands,并观察线程计数随时间的变化(启动一个打印统计数据的计时器)


    我的猜测是,我们将看到消耗的线程远远少于100个(这意味着异步行为的这一部分正在工作)。出于某种原因,SqlCommand使用了“错误”的线程池线程,但这可能根本不会降低可伸缩性。

    我很困惑。。。我们期望回调在不同的线程上执行。这就是使用Begin*…的主要目的。。。?注意:使用Begin/End回调来打开等待句柄是毫无意义的-如果你要在调用方等待,你最好根本不要使用Begin*。@MarcGravel,我想问题是为什么在第二种情况下使用工作线程而不是IOCP。I/O完成端口在简单的I/O请求中可用,由重叠的读/写文件()调用启动。SQL I/O请求并不是一件简单的事情,一大块巨大的软件位于“SQL本机客户端”之间。以及System.Data.SqlClient中的一段C++/CLI代码。TDS是协议,SNI是接口,通道可以命名为管道、套接字或共享内存。我们所观察到的仅仅意味着你的回调是在一个工作线程上执行的。但是IO可能仍然作为IOCP执行。这才是最重要的,因为它可以让您拥有数千个未完成的操作,而无需数千个线程。请试试这个实验。