You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

如何初始化Semaphore让父线程等待三个子线程全部执行完成?

信号量初始化与线程同步问题解答

首先明确核心需求:父线程必须在3个子线程全部执行完sem_post()后才能继续执行(结束)。

你的思路问题点

你想初始化sem_init(&s, 1, -2)是非法的:POSIX标准明确规定,sem_init()的第三个参数(信号量初始值)必须是非负整数,设置负数会触发未定义行为,根本不能这么用。

退一步说,即便允许初始值为负,你的担心也成立:sem_post()的逻辑是,只要有线程阻塞在sem_wait()上,不管信号量增量后的值是否仍小于0,都会唤醒一个阻塞线程。所以第一个子线程执行sem_post()时,父线程就会被唤醒,此时另外两个子线程可能还没完成,完全不符合需求。

正确的实现方式

1. 信号量初始化

sem_init(&s, 0, 0):

  • 第二个参数0:表示信号量仅在当前进程的线程间共享(因为你是同一进程内创建子线程,不需要进程间共享);
  • 第三个参数0:信号量初始值为0。

2. 父线程代码修改

父线程需要调用三次sem_wait(&s),对应三个子线程的sem_post():

sem_t s;

int main(int argc ,char *argv[]) {
    thread_t p1, p2, p3;

    sem_init(&s, 0, 0);

    thread_create(&p1, child);
    thread_create(&p2, child);
    thread_create(&p3, child);

    // 等待三个子线程全部完成
    sem_wait(&s);
    sem_wait(&s);
    sem_wait(&s);
}

逻辑说明

  • 初始信号量值为0,父线程调用第一次sem_wait()时会阻塞;
  • 每个子线程完成任务后调用sem_post(),信号量值加1,同时唤醒一个阻塞的sem_wait();
  • 三次sem_post()执行完毕后,父线程的三次sem_wait()全部完成,才能继续执行后续逻辑(结束进程),保证了三个子线程都已完成。

补充说明

如果一定要让父线程只调用一次sem_wait(),单纯靠信号量无法实现,需要结合计数器+条件变量等其他同步机制,但题目限定用信号量的话,三次sem_wait()是最直接合规的方案。

内容的提问来源于stack exchange,提问作者Lorenzo

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.07.01 16:32:39