线程其实就是进程内部的一条执行路径或控制序列。
一个进程在同一时刻只做一件事情。有了多个控制线程以后,在程序设计时可以把进程设计成在同一时刻能够做不止一件事,每个线程处理各自独立的任务。
优点
缺点
定义如下:
#include
int pthread_create(pthread_t * thread, pthread_attr_t * attr,
void * (*start_routine)(void *), void * arg);
线程一旦被创建好,内核就可以调度内核线程来执行start_routine函数指针所指向的函数了,函数结束的时候调用pthread_exit(),以确保安全的退出。
#include
void pthread_exit(void *retval);
一个进程中的所有线程都可以调用pthread_join()函数来回收其他的线程,即就是等待其他的线程结束,这类似于回收进程的wait()系统调用。pthread_join()定义如下:
#include
int pthread_join(pthread_t thread, void **thread_return);
可能的错误码如下:
错误码 | 描述 |
---|---|
EDEADLK | 可能引起死锁,比如两个线程互相针对对方调用pthread_join(),或者对自身调用pthread_join() |
EINVAL | 目标线程是不可回收的,或者已经有线程在回收该目标线程 |
ESRCH | 目标线程不存在 |
a.c
#include
#include
#include
#include
#include
#include
void* thread_fun(void* arg)
{
int i=0;
for(;i<10;i++)
{
printf("fun run\n");
sleep(1);
}
pthread_exit("fun over\n");
}
int main()
{
pthread_t id;
pthread_create(&id,NULL,thread_fun,NULL); //开启线程
int i=0;
for(;i<5;i++)
{
printf("main run\n");
sleep(1);
}
//pthread_exit(NULL);
char*s=NULL;
pthread_join(id,(void**)&s); //等待子线程
printf("s=%s\n",s);
printf("main over\n");
}
b.c
#include
#include
#include
#include
#include
#include
#define MAXID 5
void* thread_fun(void* arg)
{
int index=(int)arg;
int i=0;
for(;i<4;i++)
{
printf("index=%d\n",index);
sleep(1);
}
}
int main()
{
pthread_t id[MAXID];
int i=0;
for(;i<MAXID;i++)
{
pthread_create(&id[i],NULL,thread_fun,(void*)i);
}
for(i=0;i<MAXID;++i)
{
pthread_join(id[i],NULL);
}
exit(0);
}
使用信号量控制的线程函数
#include
#include
#include
#include
#include
#include
#include
#define MAXID 5
sem_t sem;
int g =0;
void* thread_fun(void* arg)
{
int index=*((int*)arg);
int i=0;
for(;i<1000;i++)
{
sem_wait(&sem);
printf("g=%d\n",++g);
sem_post(&sem);
}
}
int main()
{
pthread_t id[MAXID];
sem_init(&sem,0,1);
int i=0;
for(;i<MAXID;i++)
{
pthread_create(&id[i],NULL,thread_fun,(void*)&i);
}
for(i=0;i<MAXID;++i)
{
pthread_join(id[i],NULL);
}
sem_destroy(&sem);
exit(0);
}
sem.c
#include
#include
#include
#include
#include
#include
#include
sem_t sem;
void* pthread_fun(void*arg)
{
int i=0;
for(;i<5;i++)
{
sem_wait(&sem);//p
write(1,"A",1);
int n=rand()%3;
sleep(n);
write(1,"A",1);
sem_post(&sem);//v
sleep(n);
}
}
int main()
{
sem_init(&sem,0,1);
pthread_t id;
pthread_create(&id,NULL,pthread_fun,NULL);
int i=0;
for(;i<5;i++)
{
sem_wait(&sem);//p
write(1,"B",1);
int n=rand()%3;
sleep(n);
write(1,"B",1);
sem_post(&sem);//v
sleep(n);
}
pthread_join(id,NULL);
sem_destroy(&sem);
exit(0);
}
lock.c
#include
#include
#include
#include
#include
#include
#include
//sem_t sem;
pthread_mutex_t mutex;
void* pthread_fun(void*arg)
{
int i=0;
for(;i<5;i++)
{
pthread_mutex_lock(&mutex);
//sem_wait(&sem);//p
write(1,"A",1);
int n=rand()%3;
sleep(n);
write(1,"A",1);
//sem_post(&sem);//v
pthread_mutex_unlock(&mutex);
sleep(n);
}
}
int main()
{
//sem_init(&sem,0,1);
pthread_mutex_init(&mutex,NULL);
pthread_t id;
pthread_create(&id,NULL,pthread_fun,NULL);
int i=0;
for(;i<5;i++)
{
//sem_wait(&sem);//p
pthread_mutex_lock(&mutex);//p
write(1,"B",1);
int n=rand()%3;
sleep(n);
write(1,"B",1);
//sem_post(&sem);//v
pthread_mutex_unlock(&mutex);//v
sleep(n);
}
pthread_join(id,NULL);
//sem_destroy(&sem);
pthread_mutex_destroy(&mutex);
exit(0);
}
cond.c
#include
#include
#include
#include
#include
#include
pthread_mutex_t mutex;
pthread_cond_t cond;
void*fun1(void*arg)
{
char*s=(char*)arg;
while(1)
{
pthread_mutex_lock(&mutex);
pthread_cond_wait(&cond,&mutex);
pthread_mutex_unlock(&mutex);
printf("fun1:buff=%s\n",s);
if(strncmp(s,"end",3)==0)
{
break;
}
}
}
void*fun2(void*arg)
{
char*s=(char*)arg;
while(1)
{
pthread_mutex_lock(&mutex);
pthread_cond_wait(&cond,&mutex);
pthread_mutex_unlock(&mutex);
printf("fun2:buff=%s\n",s);
if(strncmp(s,"end",3)==0)
{
break;
}
}
}
int main()
{
pthread_t id[2];
char buff[128]={0};
pthread_mutex_init(&mutex,NULL);
pthread_cond_init(&cond,NULL);
pthread_create(&id[0],NULL,fun1,(void*)buff);
pthread_create(&id[1],NULL,fun2,(void*)buff);
while(1)
{
fgets(buff,128,stdin);
if(strncmp(buff,"end",3)==0)
{
//唤醒所有线程
pthread_mutex_lock(&mutex);
pthread_cond_broadcast(&cond);
pthread_mutex_unlock(&mutex);
break;
}
else
{
//唤醒一个线程
pthread_mutex_lock(&mutex);
pthread_cond_signal(&cond);
pthread_mutex_unlock(&mutex);
}
}
pthread_join(id[0],NULL);
pthread_join(id[1],NULL);
exit(0);
}
test.c
#include
#include
#include
#include
#include
#include
#include
#define MAXID 5
void* thread_fun(void* arg)
{
char str[]={"a b c d e f g h i j k l "};
char*s1=NULL;
char*s=strtok_r(str," ",&s1); //线程安全的字符串分割函数strtok_r()
while(s!=NULL)
{
printf("s=%s\n",s);
sleep(1);
s=strtok_r(NULL," ",&s1);
}
}
int main()
{
pthread_t id;
pthread_create(&id,NULL,thread_fun,NULL);
char arr[]={"1 2 3 4 5 6 7 8 9 10"};
char*p1=NULL;
char*p=strtok_r(arr," ",&p1);
while(p!=NULL)
{
printf("p=%s\n",p);
sleep(1);
p=strtok_r(NULL," ",&p1);
}
pthread_join(id,NULL);
exit(0);
}