gpt4 book ai didi

来回发送的条件变量

转载 作者:行者123 更新时间:2023-11-30 15:34:48 26 4
gpt4 key购买 nike

我有一个程序,我希望能够在不同线程之间切换。在这个例子中,我只是尝试打印一个字符串中的内容,以及另一个字符串中的内容,只是为了看看我是在两个线程之间发送的。我无法使用我的代码执行此操作,因为它挂起。理想情况下,我希望能够处理多个信号并能够来回切换。我花了大约四个小时在这上面,但我无法让它工作,我认为仅使用全局变量会更简单,然后我只需要使用互斥体而不是条件变量,或者甚至根本没有互斥锁。

我就是无法让这些变化无常的互斥锁和条件变量按预期运行。

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

char word1[10] = "Hello";
char word2[10] = "world";

pthread_mutex_t mutex = PTHREAD_MUTEX_INITIALIZER; // mutual exclusion lock for prod
//pthread_mutex_t mutexSigalProd = PTHREAD_MUTEX_INITIALIZER;
//pthread_cond_t signalToProd = PTHREAD_COND_INITIALIZER;
pthread_cond_t addToQ = PTHREAD_COND_INITIALIZER;


void * prod(void *arg) { printf("Entering prod \n");
pthread_mutex_lock(&mutex);
int i = 0;

while (i < 10) {
printf("PROD adding line: %c \t", word1[i]);
i++;
if (i % 2 == 0)
{
pthread_mutex_unlock(&mutex);
pthread_cond_signal(&addToQ);
pthread_cond_wait(&addToQ, &mutex);
}
}
pthread_exit(NULL);
}


void * con(void *arg)
{
printf("Entering con \n");
pthread_mutex_lock(&mutex);
//pthread_mutex_unlock(&mutex);
pthread_cond_wait(&addToQ, &mutex);
int i = 0;

while (i < 10)
{
printf ("CON adding line: %c \t", word2[i]);
i++;
if (i % 2 != 0)
{
//pthread_mutex_unlock(&mutex);
pthread_cond_signal(&addToQ);
pthread_cond_wait(&addToQ, &mutex);
}
}

pthread_exit(NULL);
}

int main()
{
pthread_t threadp1; // Thread objects
pthread_t threadp2;
pthread_t threadc1;

pthread_create(&threadp1, NULL, prod, NULL); // start first producer thread
//pthread_create(&threadp2, NULL, con1, NULL); // start second producer thread
pthread_create(&threadc1, NULL, con, NULL); // start consumer thread
pthread_exit(NULL); // main thread quits
}

最佳答案

代码中的竞争条件是:

Prod 发送信号而不检查 Con 是否正在等待它。如果 Con 尚未等待信号,则信号无效(来自手册页 - “如果 cond 当前没有阻塞线程,则 pthread_cond_broadcast() 和 pthread_cond_signal() 函数应无效。”)。

然后 Con 和 Prod 就会互相等待。因此陷入了僵局。

看看下面的代码是否有效:

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

char word1[10] = "Hello";
char word2[10] = "world";
int con_started = 0;

pthread_mutex_t mutex = PTHREAD_MUTEX_INITIALIZER; // mutual exclusion lock for prod
pthread_cond_t addToQ = PTHREAD_COND_INITIALIZER;

void * prod(void *arg) {
printf("PROD: Entering prod \n");
fflush(stdout);
int i = 0;
int j = 1;
while (i < 5) {
printf("PROD adding line: %c \n", word1[i]);
fflush(stdout);
i++;
if (i % 2 == 0)
{
pthread_mutex_lock(&mutex);
while(!con_started)
{
pthread_mutex_unlock(&mutex);
sched_yield();
printf("PROD: Waiting for CON to wait.\n");
fflush(stdout);
pthread_mutex_lock(&mutex);
}
printf("PROD: Sending signal %d\n\n", j);
fflush(stdout);
pthread_cond_signal(&addToQ);
printf("PROD: Will wait now \n\n");
fflush(stdout);
pthread_cond_wait(&addToQ, &mutex);
printf("PROD received signal %d\n\n", j);
fflush(stdout);
pthread_mutex_unlock(&mutex);
j++;
}
}
sched_yield();
sleep(1);
printf("PROD: Sending signal %d\n\n", j);
fflush(stdout);
pthread_cond_signal(&addToQ);
pthread_exit(NULL);
}


void * con(void *arg)
{
int i = 0;
int j=1;
printf("CON: Entering con \n");
fflush(stdout);
pthread_mutex_lock(&mutex);
con_started = 1;
printf("CON: Will wait now\n \n");
fflush(stdout);
pthread_cond_wait(&addToQ, &mutex);
printf("CON received first signal\n\n");
fflush(stdout);
while (i < 5)
{
printf ("CON adding line: %c \n", word2[i]);
fflush(stdout);
if (i % 2 != 0)
{
//pthread_mutex_unlock(&mutex);
printf("CON: Sending signal %d\n\n", j);
fflush(stdout);
pthread_cond_signal(&addToQ);
j++;
printf("CON: Will wait now \n\n");
fflush(stdout);
pthread_cond_wait(&addToQ, &mutex);
printf("CON received signal %d\n\n", j);
fflush(stdout);
pthread_mutex_unlock(&mutex);
}
i++;
}
pthread_exit(NULL);
}

int main()
{
pthread_t threadp1; // Thread objects
pthread_t threadc1;
pthread_create(&threadp1, NULL, prod, NULL); // start first producer thread
pthread_create(&threadc1, NULL, con, NULL); // start consumer thread
pthread_join(threadp1, NULL);
printf("MAIN: threadp1 completed.\n");
fflush(stdout);
pthread_join(threadc1, NULL);
printf("MAIN: threadc1 completed.\n");
fflush(stdout);
}

关于来回发送的条件变量,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/23173028/

26 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com