> 文章列表 > Linux多线程-3

Linux多线程-3

Linux多线程-3

在之前的两篇博客当中,我们讲述了线程概念、线程控制和线程安全三部分内容。紧随其后本篇博客内容:我们首先来讲述生产者和消费者模型,来了解一种多线程的设计模式,然后在此基础上讲述上一篇博客剩余的内容:信号量的相关接口并写代码实现。

目录

1.生产者与消费者模型

1.1内容

1.2优点

1.3实现

2.信号量

2.1内容

2.2接口

2.3实现

1.生产者与消费者模型

1.1内容

生产者与消费者模型是一种典型的设计模式(针对典型应用场景的解决方案),针是对存在大量数据产生以及处理的场景的一种设计模式。

在原始的操作当中,将数据的产生和获取放在同一个线程中执行,这样会造成程序的大部分时间都用于数据处理,容易造成数据资源获取不及时而被丢弃。

所以我们可以采用生产者与消费之模型,其本质是:将数据产生和处理分离处理,生产者有生产者线程,消费者有消费者线程。生产者只负责数据的获取,消费者只负责数据的处理,两个线程最终通过一个缓冲区(数据队列)来实现数据交互。

1.2优点

  1. 解耦合(防止不同函数传递参数内容过于相似);
  2. 支持忙闲不均(数据资源产生和处理大小可以不同);
  3. 支持并发;

1.3实现

结合上述内容中生产者与消费者模型的本质,我们主要需要完成的内容便是:实现一个线程安全的阻塞队列和创建生产者和消费者线程。

对上述代码编译并执行便可得到结果如下:

我们可以很直观的看到生产者和消费者模型的作用,即同时兼顾数据的输入和输出。这样我们便可用于大量数据的分解处理,提高数据资源的处理效率。

2.信号量

2.1内容

对于信号量的内容,我们再进程间通信(ipc)-3这篇博客中讨论过,没有阅读过的读者可以点击下面连接进行查看。

Linux进程间通信-3_王大可~的博客-CSDN博客

2.2接口

信号量中的接口函数都是在POSIX标准之下,

信号量变量类型:sem_t,头文件:#include<semaphore.h>。

int sem_init(sem_t *sem, int pshared, int val);

sem_init接口用于信号量初始化,其中sem是我们定义的信号量变量;pshared:0 -- 线程间;!0 -- 进程间(共享内存);val是信号量初始值。

P操作:

int sem_wait(sem_t *sem);

sem_wait是阻塞接口。

int sem_trywait(sem_t *sem);

 sem_trywait是非阻塞接口。

int sem_timedwait(sem_t *sem, struct timespec *spec);

sem_timedwait是存在设置时长的阻塞接口。

V操作:

int sem_pos(sem_t *sem);

 信号量的销毁:

int sem_destroy(sem_t *sem);

2.3实现

在了解完信号量的内容和相关操作接口时,我们来编写代码实现一个线程安全的环形队列。

最后编译并执行可以得到结果如下所示: