c - 使用 pthreads 作为带队列的线程池?

标签 c

我对 C 很陌生,如果这个问题很不对劲,我很抱歉。我已经使用 Java 执行器服务来制作固定线程池,但无法理解如何在 C 中执行类似的操作。

我学会了如何使用 pthreads 在 c 中创建线程(这看起来很简单),但我不确定如何创建一个由固定数量的线程消耗的队列?到目前为止,我完成的所有教程要么在主语句中自行启动线程,要么在 for 循环中启动线程。如果我采用这种方法,那么当我想要的只是 3 或 4 个线程时,我将拥有数百万个线程(每个工作项 1 个),并让它们处理队列。

这可能吗?如果可以的话我需要学习什么?如果 pthread 无法实现,那么我很乐意使用其他东西,我正在 Mac 上进行开发,并将其部署在 Linux 上。

最佳答案

您可以通过使用条件变量,通过单生产者/多消费者模型相当轻松地完成此操作。请记住,这是一个架构,其他架构当然也是可能的。

在主线程中,您只需创建队列、互斥体和条件变量,然后启动任意数量的线程运行,伪代码如:

glbQueue = []
glbMutex = new mutex
glbCondVar = new condvar
for i = 1 to 10:
    start thread using thrdFn

下一步是将您需要的任何工作项添加到队列中(使用互斥锁)并启动条件变量以根据需要唤醒线程:

while workitem = getNextWorkItem():
    lock glbMutex
    glbQueue.append (workItem)
    kick glbCondVar
    unlock glbMutex

所有工作项完成后,您等待队列清空,然后发布一些哨兵项来关闭线程,然后等待它们完成后再退出。

lock glbMutex
while glbQueue is not empty:
    kick glbCondVar
    unlock glbMutex.
    sleep for a bit
    lock glbMutex
unlock glbMutex.

for i = 1 to 10:
    lock glbMutex
    glbQueue.append (endWorkItem)
    kick glbCondVar
    unlock glbMutex.
    wait for any one thread to exit
exit

执行该工作的线程也相对简单。首先,它们在无限循环中运行,等待条件变量被踢出。在该循环中,他们处理工作项,直到没有更多可用的工作项,然后返回 sleep 状态。

一旦线程接收到最终工作项,它就会退出,从而保证每个线程都获得一个最终项。

换句话说,类似于:

initialise
stillGoing = true
lock glbMutex
while stillGoing:
    wait on glbCondVar using glbMutex
    while stillGoing and glbQueue is not empty:
        extract workItem from glbQueue to thread local storage
        unlock glbMutex.
        if workItem is endWorkItem:
            stillGoing = false
        else:
            do the work specified by workItem
        lock glbMutex
unlock glbMutex
clean up
exit thread

这基本上允许您有固定数量的线程处理队列上的项目,并且队列本身受到互斥体的保护,因此工作线程或主线程之间不会出现争用。

关于c - 使用 pthreads 作为带队列的线程池?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/10865865/

相关文章:

C程序不会打印链表中的节点

c++ - C++ 中的 "-->"运算符是什么?

c - 如何在我的程序中计算百分比

c - LNK1112 : module machine type 'IA64' conflicts with target machine type 'X86'

c - 对字符数组进行冒泡排序

c - 以最有效的方式读取 CGI POST 数据

c - 读取内存时避免编译器优化

c - 学生平均数的链表程序

c++ - 如何从 lua_topointer 访问 lua 的对象?

c - 包含 .c 文件有什么好处?