LeetCode //C - 1195. Fizz Buzz Multithreaded
1195. Fizz Buzz Multithreaded
You have the four functions:
- printFizz that prints the word “fizz” to the console,
- printBuzz that prints the word “buzz” to the console,
- printFizzBuzz that prints the word “fizzbuzz” to the console, and
- printNumber that prints a given integer to the console.
You are given an instance of the class FizzBuzz that has four functions: fizz, buzz, fizzbuzz and number. The same instance of FizzBuzz will be passed to four different threads:
- Thread A: calls fizz() that should output the word “fizz”.
- Thread B: calls buzz() that should output the word “buzz”.
- Thread C: calls fizzbuzz() that should output the word “fizzbuzz”.
- Thread D: calls number() that should only output the integers.
Modify the given class to output the series [1, 2, “fizz”, 4, “buzz”, …] where the i t h i^{th} ith token (1-indexed) of the series is:
- “fizzbuzz” if i is divisible by 3 and 5,
- “fizz” if i is divisible by 3 and not 5,
- “buzz” if i is divisible by 5 and not 3, or
- i if i is not divisible by 3 or 5.
Implement the FizzBuzz class:
- FizzBuzz(int n) Initializes the object with the number n that represents the length of the sequence that should be printed.
- void fizz(printFizz) Calls printFizz to output “fizz”.
- void buzz(printBuzz) Calls printBuzz to output “buzz”.
- void fizzbuzz(printFizzBuzz) Calls printFizzBuzz to output “fizzbuzz”.
- void number(printNumber) Calls printnumber to output the numbers.
Example 1:
Input: n = 15
Output: [1,2,“fizz”,4,“buzz”,“fizz”,7,8,“fizz”,“buzz”,11,“fizz”,13,14,“fizzbuzz”]
Example 2:
Input: n = 5
Output: [1,2,“fizz”,4,“buzz”]
Constraints:
- 1 <= n <= 50
From: LeetCode
Link: 1195. Fizz Buzz Multithreaded
Solution:
Ideas:
- Maintain a shared counter cur.
- Use four semaphores, one for each thread.
- Initially semNumber = 1 because sequence starts at 1.
- After a thread prints its value, it increments cur and signals the semaphore corresponding to the next value.
- When cur > n, wake all waiting threads so they can exit cleanly.
Code:
#include <stdlib.h>
#include <pthread.h>
#include <semaphore.h>
typedef struct {
int n;
int cur;
sem_t semFizz;
sem_t semBuzz;
sem_t semFizzBuzz;
sem_t semNumber;
pthread_mutex_t mutex;
} FizzBuzz;
FizzBuzz* fizzBuzzCreate(int n) {
FizzBuzz* obj = (FizzBuzz*)malloc(sizeof(FizzBuzz));
obj->n = n;
obj->cur = 1;
sem_init(&obj->semFizz, 0, 0);
sem_init(&obj->semBuzz, 0, 0);
sem_init(&obj->semFizzBuzz, 0, 0);
sem_init(&obj->semNumber, 0, 1);
pthread_mutex_init(&obj->mutex, NULL);
return obj;
}
// Don't change the following declarations
void printNumber(int a);
void printFizz();
void printBuzz();
void printFizzBuzz();
static void nextTurn(FizzBuzz* obj) {
if (obj->cur > obj->n) {
sem_post(&obj->semFizz);
sem_post(&obj->semBuzz);
sem_post(&obj->semFizzBuzz);
sem_post(&obj->semNumber);
return;
}
if (obj->cur % 15 == 0)
sem_post(&obj->semFizzBuzz);
else if (obj->cur % 3 == 0)
sem_post(&obj->semFizz);
else if (obj->cur % 5 == 0)
sem_post(&obj->semBuzz);
else
sem_post(&obj->semNumber);
}
// printFizz() outputs "fizz".
void fizz(FizzBuzz* obj) {
while (1) {
sem_wait(&obj->semFizz);
pthread_mutex_lock(&obj->mutex);
if (obj->cur > obj->n) {
pthread_mutex_unlock(&obj->mutex);
break;
}
printFizz();
obj->cur++;
nextTurn(obj);
pthread_mutex_unlock(&obj->mutex);
}
}
// printBuzz() outputs "buzz".
void buzz(FizzBuzz* obj) {
while (1) {
sem_wait(&obj->semBuzz);
pthread_mutex_lock(&obj->mutex);
if (obj->cur > obj->n) {
pthread_mutex_unlock(&obj->mutex);
break;
}
printBuzz();
obj->cur++;
nextTurn(obj);
pthread_mutex_unlock(&obj->mutex);
}
}
// printFizzBuzz() outputs "fizzbuzz".
void fizzbuzz(FizzBuzz* obj) {
while (1) {
sem_wait(&obj->semFizzBuzz);
pthread_mutex_lock(&obj->mutex);
if (obj->cur > obj->n) {
pthread_mutex_unlock(&obj->mutex);
break;
}
printFizzBuzz();
obj->cur++;
nextTurn(obj);
pthread_mutex_unlock(&obj->mutex);
}
}
// You may call global function `void printNumber(int x)`
// to output "x", where x is an integer.
void number(FizzBuzz* obj) {
while (1) {
sem_wait(&obj->semNumber);
pthread_mutex_lock(&obj->mutex);
if (obj->cur > obj->n) {
pthread_mutex_unlock(&obj->mutex);
break;
}
printNumber(obj->cur);
obj->cur++;
nextTurn(obj);
pthread_mutex_unlock(&obj->mutex);
}
}
void fizzBuzzFree(FizzBuzz* obj) {
sem_destroy(&obj->semFizz);
sem_destroy(&obj->semBuzz);
sem_destroy(&obj->semFizzBuzz);
sem_destroy(&obj->semNumber);
pthread_mutex_destroy(&obj->mutex);
free(obj);
}
更多推荐



所有评论(0)