C信号量未按预期锁定
我一直在尝试通过这个简单的售票程序学习信号灯。唯一的问题是,当前使用的信号量没有保护C信号量未按预期锁定,c,locking,semaphore,C,Locking,Semaphore,我一直在尝试通过这个简单的售票程序学习信号灯。唯一的问题是,当前使用的信号量没有保护numTickets和ticketssell的值。我发现了这一点,因为有时售出的门票总数将达到51张 是信号量的正确实现吗? #include <semaphore.h> #include <stdio.h> #include <pthread.h> #include <unistd.h> #include <time.h> int numTicket
numTickets
和ticketssell
的值。我发现了这一点,因为有时售出的门票总数将达到51张
是信号量的正确实现吗?
#include <semaphore.h>
#include <stdio.h>
#include <pthread.h>
#include <unistd.h>
#include <time.h>
int numTickets;
sem_t mySem;
void* sell_ticket(void *sellerNum) {
int sell = (int) sellerNum;
int ticketsSold = 0;
while (numTickets > 0) {
srand ( time(NULL) );
int random_number = rand();
for (int i = 1; i < random_number % 5 ; i++) {
if (numTickets > 0) {
sem_wait(&mySem);
numTickets--;
ticketsSold++;
printf("Seller # %d sold a ticket. Tickets left: %d\n", sell, numTickets);
sem_post(&mySem);
}
}
}
printf("Seller #%d noticed all tickets sold! (I sold %d myself) \n", sell, ticketsSold);
}
int main() {
numTickets = 50;
int numSellers = 4;
sem_init(&mySem, 0, 1);
pthread_t sellerThread;
for (int i = 0; i < numSellers; i++) {
pthread_create(&sellerThread, NULL, sell_ticket, (void *)i);
}
for (int i = 0; i < numSellers; i++) {
pthread_join(sellerThread, NULL);
}
printf("All tickets sold!\n");
return 0;
}
#包括
#包括
#包括
#包括
#包括
国际货币基金组织;
sem_t mySem;
作废*卖出票(作废*卖出票){
int sell=(int)sellerNum;
int ticketssell=0;
而(numTickets>0){
srand(时间(空));
int random_number=rand();
对于(int i=1;i<随机数%5;i++){
如果(numTickets>0){
sem_wait(&mySem);
numTickets——;
票务销售++;
printf(“卖家#%d卖出了一张票。剩下的票:%d\n”,卖出,numTickets);
sem_post&mySem;
}
}
}
printf(“卖家#%d注意到所有的票都卖了!(我自己也卖了%d)”,sell,ticketssell);
}
int main(){
numTickets=50;
整数=4;
sem_init(&mySem,0,1);
pthread\u t sellerThread;
对于(int i=0;i
我相信我可以看到您的代码存在两个问题:
1) 因为您要启动多个线程(每个卖家一个线程),所以您应该有一个p_线程数组,而不仅仅是一个线程。否则,pthread_join将不会连接所有创建的线程,而只连接最后一个线程(因为每次创建新线程时,都会将句柄覆盖到以前创建的线程)
您的主视图应类似于以下内容:
int main() {
numTickets = 50;
int numSellers = 4;
sem_init(&mySem, 0, 1);
pthread_t sellerThread[4];
for (int i = 0; i < numSellers; i++) {
pthread_create(&sellerThread[i], NULL, sell_ticket, (void *)i);
}
for (int i = 0; i < numSellers; i++) {
pthread_join(sellerThread[i], NULL);
}
printf("All tickets sold!\n");
return 0;
}
我不是什么pthreads专家,但是当另一个线程正在编写numTickets时,我认为读取numTickets(在
if
和while
中)是个问题。您需要在受信号量保护的块内获取读-修改-写序列。遗憾的是,经过各种测试,我得到了51的值。我已经看完了你的答案,现在我明白了在if和while周围放置信号量是多么明智的选择。遗憾的是,即使提供了代码。我偶尔会得到高于50的值。
void* sell_ticket(void *sellerNum) {
int sell = (int) sellerNum;
int ticketsSold = 0;
while (true) {
// Check the number of tickets left. If sold out break out of infinite loop
sem_wait(&mySem);
if (numTickets <= 0) {
sem_post(&mySem);
break;
}
sem_post(&mySem);
srand ( time(NULL) );
int random_number = rand();
for (int i = 1; i < random_number % 5 ; i++) {
// Wait for semaphore before reading numTickets value in if condtion
sem_wait(&mySem);
if (numTickets > 0) {
numTickets--;
ticketsSold++;
printf("Seller # %d sold a ticket. Tickets left: %d\n", sell, numTickets);
}
// Post after if
sem_post(&mySem);
}
}
printf("Seller #%d noticed all tickets sold! (I sold %d myself) \n", sell, ticketsSold);
}