防止线程饥饿 – 最佳实践


我正在寻找有关如何防止可能在多个处理器/内核上同时运行多达 200 个线程的应用程序或服务中的线程匮乏/阻塞/竞争的更多信息。

我在网上找到的大多数示例都展示了如何在最多 3 或 4 个线程之间进行协调,我正在计划一个拥有数百个线程的应用程序。

我已经制作了运行多达 30 个线程的应用程序,但当超出这个范围时,我担心某些线程无法获得任何 CPU 时间,更不用说同步了。

我在哪里可以找到一些非常好的文章和博客?
关于这个主题的最好的书是什么?
关于这个主题有很多书籍和文章,我正在寻找最有信息性和指导性的书籍和文章,但没有以超出我理解的工程语言呈现。

感谢所有建议。

解决方案1

涉及的场景太多,无法回答您的问题。

但是,使用比核心数量更多的活动线程通常会适得其反。 仅当大多数线程通常想要休眠时,您才可以从使用多于核心数量的线程中受益,例如,通过等待某些 IO 操作,例如从网络接收数据的 recv() 调用。 即使在这种情况下,您也希望主动控制并行执行的线程数量,因此启动 200 个线程并希望其中只有 4 个线程“希望”并行运行(如果您有 4 个核心),这并不是一个好的做法。

如果您必须运行 200 个始终处于活动状态的并行任务,那么您最好只创建与核心数量相同数量的线程,并将这些任务拆分为小作业。 您可以按照您想要的顺序在线程上执行这些小作业,方法是将它们放入作业队列中,线程从作业队列中将它们一一取出。 这已经接近拥有自己的调度程序了。 一种通常会产生比前一种更复杂的解决方案的技术是使用绿色线程/协程(在某些 Linux 发行版上已弃用 ucontext POSIX api,在 Windows 上已弃用 Fiber api)。

使用绿色线程,您可以将一个线程拆分为许多绿色线程,并在用户空间中显式执行这些绿色线程之间的任务切换/协作。 假设您有 4 个核心。 然后你可以启动 4 个线程,如果你将每个线程分成 100 个绿色线程,那么你就有 400 个绿色线程,但其中只有 4 个在任何给定时间点并行执行,你可以编写自己的调度程序,因为你可以控制绿色线程之间的任务切换。

例如,使用绿色线程编写 Web 服务器具有以下好处:如果编写得好,普通多线程和异步/绿色线程实现的代码可以使用相同的 servlet 代码(因为您可以将任务切换放入您自己的实现中,否则阻塞函数调用(如套接字读/写函数)以及多线程模式下相同阻塞函数调用的实现实际上是调用阻塞操作系统等效函数)。

コメント

タイトルとURLをコピーしました