c# - 控制线程数以平衡 .NET 中的 CPU 和 IO 等待

标签 c# .net multithreading

有没有办法在 .NET 应用程序内部确定我当前是受 CPU 时间限制还是 IO 是瓶颈?

我正在查询一堆远程网络服务,其细节并不重要,可以抽象为:

// perform a single  operation
if ( [randomness] ) {
    sleep(10s of seconds); // DNS/TCP connection timeout
} else {
    sleep(10s of miliseconds); // query a remote server
}
for x = 1…lots {
    // Do some CPU intensive work
}

虽然我有 CPU 可用,但我想安排尽可能多的线程,因为它们会花费很长时间等待 IO,但是一旦 CPU 满载,我不想继续生成线程,因为会导致性能崩溃。任务总数“大”。

一个明显的答案是只选择一个“合理”的并发线程数作为调整参数,但这有两个问题:

  • “ sleep ”的长度在 LAN 往返和 TCP 连接超时之间可能会有很大差异,因此 CPU 工作与 IO 等待时间的比率可能相差 3 个数量级。
  • 将运行此程序的机器大小各不相同,从小型单 CPU VM 到重量级服务器级机器不等。

在理想世界中,IO 操作将全部替换为异步完成回调,但在这种情况下这并不容易/不可能,因为网络 RPC 使用现有的阻塞代码。

最佳答案

对于这种类型的工作,实际上最好使用异步 i/o 模式,而不是生成一堆线程(或使用大量线程池线程)。

基本上,这涉及使用 BeginXxx 方法进行所有 I/O 调用,在等待结果时仅使用 I/O 完成端口。当结果返回时,它会在线程池线程上触发回调。最终结果是您的代码只会在开始调用之前以及结果返回时运行。您不会有任何线程等待响应。

关于c# - 控制线程数以平衡 .NET 中的 CPU 和 IO 等待,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/4693553/

相关文章:

c# - 我们如何在两个托管进程之间使用 "Object"的共享内存段共享数据?

c# - 如何使用已作为 IQurable 查询的 ToListAsync 变量来 Moq 设置等待?

multithreading - 继续 OS X - 两个库调用系统函数

c# - MdilXapCompile.exe 失败,错误代码为 2001

c# - 如何在grid中找到textbox的控件

javascript - 使用 Ajax 填充 Gridview

c# - 有人熟悉 Winforms 的 "sticky windows"库吗?

.net - 衡量函数、类和进程速度的最佳方法

C++ Qt5 - 程序在 QThread 之前完成

wpf - 使用 WPF 的 MVVM 模式是否不需要 Dispatcher?