首页 > 解决方案 > C ++在另一个进程之后执行一个子进程迭代

问题描述

我想创建两个子进程,其中包含一些迭代,以便进程 X 中的迭代 l 始终在进程 Y 中的迭代 l+1 之后执行。

#include <stdio.h>
#include <unistd.h>
#include <bits/stdc++.h>
#include <sys/wait.h>
#include <semaphore.h>


using namespace std;

sem_t mut;

int x = 2;
int main()
{
    int cpX = fork();
    sem_init(&mut, 1, 1);
    if (cpX == 0)
    {
        //child A code
        for (int i = 0; i < 10; i++)
        {
            sem_wait(&mut);
            cout << "Inside X:" << getpid() << ", " << i << '\n';
            sleep(rand() % 5);
        }
        
        exit(0);
    }
    else
    {
        int cpY = fork();
        if (cpY == 0)
        {
            //child B code
            for (int i = 0; i < 10; i++)
            {
                cout << "Inside Y:" << getpid() << ", " << i << '\n';
                sleep(rand() % 5);
                sem_post(&mut);
            }
            //sem_wait(&mut);
           exit(0); 
        }
        else
        {
            //sleep(50);
            
            //wait(NULL);
            //wait(NULL);
            exit(0);
            // wait(NULL);
        }
    }
}

但是在这里,X 执行一次,然后 Y 开始执行,X 不再执行。为什么会这样?

标签: c++processforksemaphore

解决方案


a 期间的父/子fork正在执行复制,因此它们不会引用相同的信号量对象。因此,mut不会像您假设的那样共享。您的代码段几乎正确,您只需要进行一些小的更改即可按预期工作。

由于您使用的是未命名的信号量,因此您需要在共享区域中实例化信号量对象:

#include <sys/mman.h>

sem_t *mut = (sem_t*)mmap(NULL, sizeof(*mut), PROT_READ |PROT_WRITE,MAP_SHARED|MAP_ANONYMOUS, -1, 0);
sem_init(mut, 1, 1);

通过这些微小的调整,您上面的代码片段现在可以按预期工作,因为它们现在指的是同一个信号量对象。

另外,一些提示:sem_post是一个非阻塞调用,而是sem_wait一个阻塞调用。您还需要注意,sem_post当此时没有人在信号量上等待时,发送的信号可能会丢失。

这类事物的最佳参考是Unix Network Programming: Interprocess Communication by Richard Stevens


推荐阅读