微信公众号搜"智元新知"关注
微信扫一扫可直接关注哦!

是否可以仅使用互斥体而不是条件变量或信号量在 c 中创建自定义障碍

如何解决是否可以仅使用互斥体而不是条件变量或信号量在 c 中创建自定义障碍

我完全迷失在 c 中实现自定义屏障只使用互斥而不使用 条件变量或信号量。我编写了一个使用互斥锁和条件变量组合的代码,但我只需要使用互斥锁来编写它,而不使用例如 pthread_cond_t 或 sth 类似的。

如果你知道怎么做,如果你能发送带有简要说明的源代码,我将不胜感激。

谢谢

这是我的源代码


#include <stdio.h>
#include <stdlib.h>
#include "pthread.h"

#define NoThreadsCreated 4

// barrier data structure
typedef struct {
    int maxCount; // maximum number of runners
    struct sub_barrier {
        pthread_mutex_t wait_lk;   // mutex for waiters at barrier
        pthread_cond_t wait_cv;   // waiting condition for waiters at barrier
        int runners;   // number of running threads
    } sub_barrier[NoThreadsCreated];
    struct sub_barrier *sbp;    // current sub_barrier
} barrier_t;

// barrier initialization function
int barrier_init(barrier_t *barrier,int count,void *arg) {
    // if less then 1 thread is being created then what the hell are we doing :)
    if (count < 1){
        return (-1);
    }
    barrier->maxCount = count;
    barrier->sbp = &barrier->sub_barrier[0];
    for (int i = 0; i < NoThreadsCreated; ++i) {
        struct sub_barrier *sbp = &(barrier->sub_barrier[i]);
        sbp->runners = count;
        // if initialising mutex faced error return -1
        if (pthread_mutex_init(&sbp->wait_lk,arg)){
            return (-1);
        }
        // if initialising thread's conditions faced error return -1
        if (pthread_cond_init(&sbp->wait_cv,arg)){
            return (-1);
        }
    }
    // if the initialization is completed correctly return 0
    return (0);
}

// barrier waiting function
int barrier_wait(barrier_t *bp) {
    struct sub_barrier *sbp = bp->sbp;
    // Locking threads with mutex
    pthread_mutex_lock(&sbp->wait_lk);
    // last thread to reach barrier
    if (sbp->runners == 1) {
        // check to see if the runners is 1 the number of threads are
        // not 1 if it was one then why do we bother multi threading :)
        if (bp->maxCount != 1) {
            // reset runner count (by doing this the while loop in line 62 will not be correct any more and other threads
            // will skip the while loop
            sbp->runners = bp->maxCount;
            // switch sub-barriers
            if(bp->sbp == &bp->sbp[0]){
                bp->sbp = &bp->sbp[1];
            }
            else{
                bp->sbp = &bp->sbp[0];
            }
            // wake up the waiters and tell them that we faced the last thread so you can
            pthread_cond_broadcast(&sbp->wait_cv);
        }
    } else {
        // as it's not the last thread,just decrease the runners by one
        sbp->runners--;
        // with the help of pthread condition we are waiting for the next thread and we do not let other threads
        // to pass and unlock the mutex,unless we find out that we reached the last thread
        while (sbp->runners != bp->maxCount){
            pthread_cond_wait(&sbp->wait_cv,&sbp->wait_lk);
        }
    }
    pthread_mutex_unlock(&sbp->wait_lk);
    return (0);
}

void *routine(barrier_t *ba) {
    printf("waiting at the barrier\n");
    for (int i = 0; i < NoThreadsCreated; ++i) {
        barrier_wait(ba);
        // do parallel computations
    }
    printf("We passed the barrier\n");
    return NULL;
}

int main() {
    int i;
    barrier_t bar;
    pthread_t *tid;

    // initialising barrier (note that we want also have main thread
    barrier_init(&bar,NoThreadsCreated+1,NULL);
    tid = (pthread_t *) calloc(NoThreadsCreated,sizeof(pthread_t));
    // creating threads
    for (i = 0; i < NoThreadsCreated; ++i) {
        if (pthread_create(&tid[i],NULL,(void *(*)(void *)) routine,&bar) != 0) {
            perror("thread_creation");
            exit(1);
        }
    }
    // doing parallel computations // critical section
    for (i = 0; i < NoThreadsCreated; i++) {
        barrier_wait(&bar);
        // do parallel computations
    }
    // joining threads
    for (i = 0; i < NoThreadsCreated; i++) {
        if(pthread_join(tid[i],NULL) != 0){
            perror("thread_join");
            exit(1);
        }
    }

    return 0;
}

版权声明:本文内容由互联网用户自发贡献,该文观点与技术仅代表作者本人。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如发现本站有涉嫌侵权/违法违规的内容, 请发送邮件至 dio@foxmail.com 举报,一经查实,本站将立刻删除。

相关推荐


Selenium Web驱动程序和Java。元素在(x,y)点处不可单击。其他元素将获得点击?
Python-如何使用点“。” 访问字典成员?
Java 字符串是不可变的。到底是什么意思?
Java中的“ final”关键字如何工作?(我仍然可以修改对象。)
“loop:”在Java代码中。这是什么,为什么要编译?
java.lang.ClassNotFoundException:sun.jdbc.odbc.JdbcOdbcDriver发生异常。为什么?
这是用Java进行XML解析的最佳库。
Java的PriorityQueue的内置迭代器不会以任何特定顺序遍历数据结构。为什么?
如何在Java中聆听按键时移动图像。
Java“Program to an interface”。这是什么意思?