【发布时间】:2018-05-13 09:04:56
【问题描述】:
如果我有 N 个套接字数组,并且我需要以尽可能高的速度向每个套接字发送(..)数据,那么执行此操作的最佳线程数是多少?操作系统是linux。
例如如果我有 C 物理内核,是否应该是每个执行发送(..)的 C 线程?会有效率吗?换句话说,我的问题是 linux 内核如何处理 send(..) 系统调用以及提供给它的数据将如何在内核中调度。我记得从 BSD 套接字文档中读到,实际上所有套接字的 send(..) 系统调用都将数据放入由一个线程处理的队列中,因此代码:
thread1 -> send(sock1, ..)
..
threadN -> send(sockN, ..)
将或多或少等同于代码的网络性能(减去在发送到内核之前通过发送处理数据的时间)
thread -> send(sock1, ..), ..., send(sockN, ..)
但那是 1990 年中期的书,我认为现代操作系统应该在那之后改变。
【问题讨论】:
-
我的个人经验,尽量让系统尽可能高效。试着让它比需要的效率稍微高一点。这种策略具有最佳的结果与努力比。为什么您需要系统超级高效?
-
我正在审查在特定(罕见)时间段需要向大量套接字发送大量消息的软件代码。例如。每小时一次,它尽可能快地向 100 个套接字发送 100 条不同的消息(每个套接字发送 1 条消息)。目前他们有 100 个线程的解决方案,我认为这不是有效的(他们有 10/20 个物理/虚拟内核)。与开发人员争论,试图了解正确的方法。
-
好吧,我已经在 1 个单线程中为 150 台设备完成了这项工作。每个得到一个大小为 128 字节的消息有效负载。因此,在这种情况下,多线程效率不高。将整个事情放在一个 for 循环中就足够了。此外,在 1 轮完整的发送消息结束时,我让循环休眠了 10 微秒。这将 CPU 使用率从 82% 降低到 12%。
-
如果您向 100 个线程发送 100 条消息,则无需回答任何问题。您需要与套接字一样多的线程,并且摆弄它只会使其变慢。任何特定套接字的
send()已经在内核中进行了序列化,并且网络本质上已经将出站数据序列化到所有目的地。让操作系统完成它的工作。不要试图帮助它。
标签: c++ linux multithreading sockets