1, Functional requirements
Three threads are used. Thread 1 is used to listen to user input and as listener of other two threads. The main content of thread 2 is to output "hello 2" string every other period of time. Thread 3 is used to output "hello 3" string every other period of time. Change the state of thread 1 and thread 2 according to the input data
To realize the creation, pause, recovery, termination and other operations of threads, and control them by inputting numbers. Specifically, after creation, they are suspended by default,
- 1 resume thread 2, 2 pause thread 2, 3 terminate thread 2,
- 5 resume thread 3, 6 pause thread 3, 7 terminate thread 3.
Among them, resume and pause can be repeated alternately.
2, Main function
pthread_create: create thread function in UNIX Environment
pthread_join: used to wait for the end of a thread.
The first two and the last two are used in pairs, which can be used alternately according to the needs of the scene
pthread_mutex_lock: mutually exclusive lock
pthread_mutex_unlock: mutex unlock
pthread_cond_signal: conditional wake up
pthread_cond_wait: conditional wait
3, Running screenshot
Why can't threads be suspended / suspended immediately? When inputting 2 or 6, threads 2 and 3 will have an output?
Answer: the input read in thread 1 and the pause / suspend operation executed in threads 2 and 3 cannot respond immediately
4, Main code
#include<stdio.h> #include<pthread.h> #include<unistd.h> /* 1 Resume thread 2, 2 pause thread 2, 3 terminate thread 2, 5 Resume thread 3, 6 pause thread 3, 7 terminate thread 3. */ static int input=0; //Receive keyboard input static pthread_t id1,id2,id3;//Threads 1, 2, 3 //Conditional variable and mutex initialization pthread_cond_t c2 = PTHREAD_COND_INITIALIZER; pthread_cond_t c3 = PTHREAD_COND_INITIALIZER; pthread_mutex_t m2 = PTHREAD_MUTEX_INITIALIZER; pthread_mutex_t m3 = PTHREAD_MUTEX_INITIALIZER; //Thread 1 void FunOne(void) { //First start blocking thread 2, 3 pthread_mutex_lock(&m2); pthread_mutex_lock(&m3); while(1) { scanf("%d", &input); switch(input) { case 1: //Resume thread 2; printf("Resume thread 2...\n"); pthread_cond_signal(&c2);//Send a signal to wake up the waiting process pthread_mutex_unlock(&m2);//It will be called multiple times in the while loop break; case 3: //Terminate thread 2; pthread_cancel(id2); printf("Terminate thread 2...\n"); break; case 5: //Resume thread 3; printf("Resume thread 3...\n"); pthread_cond_signal(&c3); pthread_mutex_unlock(&m3); break; case 7: //Terminate thread 3; pthread_cancel(id3); printf("Terminate thread 3...\n"); break; } } } //Thread 2 void FunTwo(void) { pthread_mutex_lock(&m2); while(1) { if(input==2) { printf("Suspend thread 2...\n"); pthread_cond_wait(&c2, &m2);//The thread executing this function will be suspended } else { sleep(2); printf("hello 2! \n"); } } pthread_mutex_unlock(&m2); } //Thread 3 void FunThree(void) { pthread_mutex_lock(&m3); while(1) { if(input==6) { printf("Suspend thread 3...\n"); pthread_cond_wait(&c3, &m3);//The thread executing this function will be suspended } else { sleep(2); printf("hello 3! \n"); } } pthread_mutex_unlock(&m3); } int main(int argc,char* argv[]) { int res1 = pthread_create (&id1, NULL, (void *) FunOne, NULL); sleep(1);//Let thread 1 seize the cpu first, and let threads 2 and 3 block through the mutex int res2 = pthread_create (&id2, NULL, (void *) FunTwo, NULL); int res3 = pthread_create (&id3, NULL, (void *) FunThree, NULL); if(res1!=0||res2!=0||res3!=0) { printf("create error!\n"); return -1; } /** *Block the process to execute the specified thread */ pthread_join(id1,NULL); pthread_join(id2,NULL); pthread_join(id3,NULL); pthread_mutex_destroy(&m2);//Destroy mutex pthread_mutex_destroy(&m3);//Destroy mutex return 0; }
5, Summary
Thread 2 and 3 are suspended for the first time because thread 1 locks the mutex first, while threads 2 and 3 are suspended because they are waiting for the condition signal
Here, we can't only use a mutex and a condition variable. When a thread mutex unlocks or sends a condition signal, it will wake up other waiting threads and can't control the execution of a certain thread. You can try to control by setting some global variables.
Code may have other problems, for reference only!