多线程

1.线程是什么

在一个程序里的一个执行路线叫做线程(thread),线程是“一个进程内部的控制序列”

2.线程和进程的区别

进程是操作系统分配资源的基本单位

线程是CPU调度的基本单位

  • 线程的优缺点

线程的优点

1.创建一个新线程的代价要比创建一个新进程小得多

2.与进程之间的切换相比,线程之间的切换需要操作系统做的操作要少很多

3.线程占用的资源要比进程少很多

4.能充分利用多处理器的可并行数量

5.在等待慢速I/O操作结束的同时,程序可执行其他的计算任务

6.计算密集型应用,为了能在多处理器系统上运行,将计算分解到多个线程中实现

7.I/O密集型应用,为了提高性能,将I/O操作重叠。线程可以同时等待不同的I/O操作。

线程缺点:

1.性能损失

2.健壮性降低

3.缺乏访问控制

4.编程难度提高

3.线程控制

线程的创建

原型

int pthread_create(pthread_t *thread, const pthread_attr_t *attr, void *(*star
t_routine)(void*), void *arg);

参数

 thread:返回线程ID

 attr:设置线程的属性,attr为NULL表示使用默认属性

 start_routine:是个函数地址,线程启动后要执行的函数

 arg:传给线程启动函数的参数

返回值:成功返回0;失败返回错误码
 

线程终止

原型

void pthread_exit(void *value_ptr);

参数

 value_ptr:value_ptr不要指向一个局部变量。

返回值:无返回值,跟进程一样,线程结束的时候无法返回到它的调用者(自身)

线程等待与分离

原型

 int pthread_join(pthread_t thread, void **value_ptr);

参数

 thread:线程ID

 value_ptr:它指向一个指针,后者指向线程的返回值

返回值:成功返回0,失败返回错误码

4.同步与互斥

(1)互斥量(mutex)

初始化:

     1.静态分配

pthread_mutex_t mutex = PTHREAD_MUTEX_INITIALIZER

     2.动态分配

int pthread_mutex_init(pthread_mutex_t *restrict mutex, const pthread_mutexattr
_t *restrict attr);

参数:

mutex:要初始化的互斥量

attr:NULL

销毁互斥量

int pthread_mutex_destroy(pthread_mutex_t *mutex);

互斥量加锁与解锁

int pthread_mutex_lock(pthread_mutex_t *mutex);
int pthread_mutex_unlock(pthread_mutex_t *mutex);

返回值:成功返回0,失败返回错误号

(2)四个死锁的必要条件

  1. 互斥条件
  2. 不可剥夺条件
  3. 请求与保持条件
  4. 环路等待条件

 

(3)条件变量函数

1.初始化

int pthread_cond_init(pthread_cond_t *restrict cond,const pthread_condattr_t *rest
rict attr);

参数:

cond:要初始化的条件变量

attr:NULL

2.销毁

int pthread_cond_destroy(pthread_cond_t *cond)

3.等待条件满足

int pthread_cond_wait(pthread_cond_t *restrict cond,pthread_mutex_t *restrict mute
x);

参数:

 cond:要在这个条件变量上等待

mutex:互斥量

4.唤醒等待

 int pthread_cond_broadcast(pthread_cond_t *cond);
 int pthread_cond_signal(pthread_cond_t *cond);

(4)生产者与消费者模型

#include<stdio.h>
  2 #include<stdlib.h>
  3 #include<unistd.h>
  4 //条件变量函数
  5 //pthread_cond_init 初始化
  6 //pthread_cond_destroy 销毁
  7 //pthread_cond_wait 等待
  8 //pthread_cond_signal 唤醒等待
  9 
 10 int noodles=0;
 11 pthread_cond_t cond;
 12 pthread_mutex_t mutex;
 13 
 14 void *thr_producer(void*arg)
 15 {
 16         int id=(int)arg;
 17         while(1)
 18         {
 19                 pthread_mutex_lock(&mutex);//加锁
 20                 while(noodles==1)
 21                 {
 22                         pthread_cond_wait(&cond,&mutex);//等待
 23                 }
 24                 printf("producer:%d on sale!!\n",id);
 25                 noodles=1;
 26                 //悄悄告诉别人,面条生产出来了
 27                 pthread_cond_signal(&cond);//唤醒等待
 28                 pthread_mutex_unlock(&mutex);//解锁
 29         }
 30         return NULL;
 31 }
 32 
 33 void *thr_consumer(void *arg)
 34 {
 35         int id=(int)arg;
 36         while(1)
 37         {
 38                 pthread_mutex_lock(&mutex);
 39                 while(noodles==0)//如果没有面条就等待
 40                 {
 41                         pthread_cond_wait(&cond,&mutex);
 42                 }
 43                 printf("consumer:%d oh my god!!!\n",id);
 44                 noodles=0;
 45                 pthread_cond_signal(&cond);//唤醒等待
 46                 pthread_mutex_unlock(&mutex);//解锁
 47         }
 48         return NULL;
 49 }
 50 
 51 int main()
 52 {
 53         pthread_t tid1,tid2;
 54         int ret,i;
 55         pthread_cond_init(&cond,NULL);//初始化条件变量函数
 56         pthread_mutex_init(&mutex,NULL);//初始化互斥量
 57         for(i=0;i<4;i++)
 58         {
 59                 ret=pthread_create(&tid1,NULL,thr_producer,(void*    )i);//创建线程
 60                 if(ret!=0)
 61                 {
 62                         printf("pthread_create error!!\n");
 63                         return -1;
 64                 }
 65         }
 66         for(i=0;i<4;i++)
 67         {
 68         ret=pthread_create(&tid2,NULL,thr_producer,(void*)i);//创
    建线程
 69                 if(ret!=0)
 70         {
 71                         printf("pthread_create error!!\n");
 72                         return -1;
 73                 }

 74         }
 75         pthread_join(tid1,NULL);//等待线程结束
 76         pthread_join(tid2,NULL);
 77         pthread_cond_destroy(&cond);//销毁
 78         pthread_mutex_destroy(&mutex);
 79         return 0;
 80 }

 

(5)POSIX信号量

1.初始化信号量

#include <semaphore.h>
int sem_init(sem_t *sem, int pshared, unsigned int value);

参数:

pshared:0表示线程间共享,非零表示进程间共享

value:信号量初始值

2.销毁信号量

int sem_destroy(sem_t *sem);

3.等待信号量

功能:等待信号量,会将信号量的值减1

int sem_wait(sem_t *sem);

4.布信号量

功能:发布信号量,表示资源使用完毕,可以归还资源了。将信号量值加1。

int sem_post(sem_t *sem);

(6)读写锁

1.初始化

int pthread_rwlock_init(pthread_rwlock_t *restrict rwlock,const pthread_rwlockattr
_t *restrict attr);

2.销毁

int pthread_rwlock_destroy(pthread_rwlock_t *rwlock);

3.加锁和解锁

int pthread_rwlock_rdlock(pthread_rwlock_t *rwlock);
int pthread_rwlock_wrlock(pthread_rwlock_t *rwlock);
int pthread_rwlock_unlock(pthread_rwlock_t *rwlock);

 

 

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值