【操作系统】多线程同步与互斥

文章目录

  • 一. 实验目的
  • 二. 实验内容
  • 三. 实验步骤
  • 四. 实验结果
  • 五. 实验总结

一. 实验目的

(1)加强对进程同步和互斥的理解,学会使用信号量解决资源共享问题。
(2)熟悉Linux 进程同步原语。
(3)掌握信号量wait/signal 原语的使用方法,理解信号量的定义、赋初值及wait/signal操作

二. 实验内容

(1)编写程序,使用Linux操作系统中的信号量机制模拟实现生产者-消费者问题。设有一个生产者和一个消费者,缓冲区可以存放产品,生产者不断生成产品放入缓冲区,消费者不断从缓冲区中取出产品,消费产品。
(2)以上实验只模拟了一个产品的放入与取出,请修改代码,以模拟实现多个产品的放入与取出。

三. 实验步骤

(1)编写程序,使用Linux操作系统中的信号量机制模拟实现生产者-消费者问题。设有一个生产者和一个消费者,缓冲区可以存放产品,生产者不断生成产品放入缓冲区,消费者不断从缓冲区中取出产品,消费产品。

#include <stdio.h>
#include <pthread.h>
#include <string.h>
#include <stdlib.h>
#include <semaphore.h>#define SIZE 256
sem_t empty, full, mutex;
char *buffer;void *producer()
{sem_wait(&empty); sem_wait(&mutex); printf("input something to buffer:\n");buffer = (char *)malloc(SIZE);fgets(buffer, SIZE, stdin);sem_post(&mutex); sem_post(&full); }void *consumer()
{sem_wait(&full); sem_wait(&mutex);printf("read product from buffer: %s\n", buffer);memset(buffer, 0, SIZE);sem_post(&mutex); sem_post(&empty); 
}int main()
{pthread_t id_producer, id_consumer;int ret;sem_init(&empty, 0, 1); sem_init(&full, 0, 0); sem_init(&mutex, 0, 1); ret = pthread_create(&id_producer, NULL, producer, NULL);ret = pthread_create(&id_consumer, NULL, consumer, NULL); pthread_join(id_producer, NULL);pthread_join(id_consumer, NULL);sem_destroy(&empty);sem_destroy(&full);sem_destroy(&mutex);printf("The End ...\n");return 0;
}

该程序实现了生产者和消费者问题的解决方案,使用了三个信号量(empty、full和mutex)来控制生产和消费的进程访问缓冲区。

首先,程序定义了一个缓冲区(buffer),大小为256字节,用于生产者和消费者的数据交换。然后,使用了三个信号量来控制进程访问缓冲区的情况,其中,empty是缓冲区为空时的信号量,full是缓冲区为满时的信号量,mutex是用于保护缓冲区的互斥锁。

在producer函数中,生产者使用了P操作(sem_wait)操作empty和mutex信号量。如果empty信号量的值大于0,则表示缓冲区未满,可以向缓冲区中添加数据,否则就需要等待。同时,使用互斥锁mutex来保证缓冲区的同步访问。之后,生产者从标准输入中读取数据,将数据添加到缓冲区,并使用V操作(sem_post)操作mutex和full信号量,以此通知消费者缓冲区已经有数据可以读取。

在consumer函数中,消费者使用了P操作操作full和mutex信号量。如果full信号量的值大于0,则表示缓冲区有数据,可以读取,否则就需要等待。同样地,使用互斥锁mutex来保证缓冲区的同步访问。之后,消费者从缓冲区中读取数据,并将缓冲区清空。最后,使用V操作操作mutex和empty信号量,以此通知生产者缓冲区已经可写入新的数据。

在main函数中,创建了生产者和消费者进程,并等待它们完成。最后,使用sem_destroy函数来销毁信号量,并输出程序结束的信息。

总之,该程序使用了信号量来实现线程之间的同步,解决了生产者和消费者问题,保证了线程安全性和数据交换的可靠性。


(2)以上实验只模拟了一个产品的放入与取出,请修改代码,以模拟实现多个产品的放入与取出。

#include <stdio.h>
#include <pthread.h>
#include <string.h>
#include <stdlib.h>
#include <semaphore.h>#define SIZE 256
sem_t empty, full, mutex;
char *buffer;void *producer()
{while(1){sem_wait(&empty); sem_wait(&mutex); printf("input something to buffer:\n");buffer = (char *)malloc(SIZE);fgets(buffer, SIZE, stdin);sem_post(&mutex); sem_post(&full); }}void *consumer()
{while(1){sem_wait(&full); sem_wait(&mutex);printf("read product from buffer: %s\n", buffer);memset(buffer, 0, SIZE);sem_post(&mutex); sem_post(&empty); }
}int main()
{pthread_t id_producer, id_consumer;int ret;sem_init(&empty, 0, 1); sem_init(&full, 0, 0); sem_init(&mutex, 0, 1); ret = pthread_create(&id_producer, NULL, producer, NULL);ret = pthread_create(&id_consumer, NULL, consumer, NULL); pthread_join(id_producer, NULL);pthread_join(id_consumer, NULL);sem_destroy(&empty);sem_destroy(&full);sem_destroy(&mutex);printf("The End ...\n");return 0;
}

该程序是一个典型的生产者消费者问题的解决方案,使用了三个信号量(empty、full和mutex)来控制生产者和消费者访问缓冲区。不同之处在于,程序使用了while(1)循环,可以使生产者和消费者持续地向缓冲区中添加或读取数据,并避免在处理完一次数据后就退出的情况发生。

程序开始时,定义了一个缓冲区(buffer),大小为256字节,用于生产者和消费者的数据交换。接着,使用了三个信号量来控制进程访问缓冲区的情况,其中,empty是缓冲区为空时的信号量,full是缓冲区为满时的信号量,mutex是用于保护缓冲区的互斥锁。

在producer函数中,生产者使用了while(1)循环,表示生产者会一直运行下去。在循环中,生产者使用了P操作(sem_wait)操作empty和mutex信号量。如果empty信号量的值大于0,则表示缓冲区未满,可以向缓冲区中添加数据,否则就需要等待。同时,使用互斥锁mutex来保证缓冲区的同步访问。之后,生产者从标准输入中读取数据,将数据添加到缓冲区,并使用V操作(sem_post)操作mutex和full信号量,以此通知消费者缓冲区已经有数据可以读取。

在consumer函数中,消费者使用了while(1)循环,表示消费者会一直运行下去。在循环中,消费者使用了P操作操作full和mutex信号量。如果full信号量的值大于0,则表示缓冲区有数据,可以读取,否则就需要等待。同样地,使用互斥锁mutex来保证缓冲区的同步访问。之后,消费者从缓冲区中读取数据,并将缓冲区清空。最后,使用V操作操作mutex和empty信号量,以此通知生产者缓冲区已经可写入新的数据。

在main函数中,创建了生产者和消费者线程,并等待它们完成。最后,使用sem_destroy函数来销毁信号量,并输出程序结束的信息。

总之,该程序使用了信号量和互斥锁来实现线程之间的同步,解决了生产者和消费者问题,保证了线程安全性和数据交换的可靠性。使用while(1)循环可以使生产者和消费者持续地向缓冲区中添加或读取数据,并提高了程序的实用性。

四. 实验结果

(1)编写程序,使用Linux操作系统中的信号量机制模拟实现生产者-消费者问题。设有一个生产者和一个消费者,缓冲区可以存放产品,生产者不断生成产品放入缓冲区,消费者不断从缓冲区中取出产品,消费产品。

1

(2)以上实验只模拟了一个产品的放入与取出,请修改代码,以模拟实现多个产品的放入与取出。

2

五. 实验总结

本实验是通过对Linux操作系统中的信号量机制进行模拟实现,来深入理解多线程同步与互斥的概念和基本方法,同时也是对生产者-消费者模型的一个实际应用。

通过本次实验,我们深入了解了信号量的概念、使用方法以及相关的函数,并通过对生产者-消费者问题的模拟,掌握了相关的同步互斥机制。在实现过程中,我们使用了一个互斥信号量mutex来控制缓冲区和生产者、消费者之间的竞争,并使用了两个信号量full,empty来分别控制缓冲区是否已满或已空,从而实现了生产者和消费者之间的同步与互斥。

在实验中,我们还发现了一些问题和需要注意的地方。例如,在使用信号量时,需要保证每次操作都是原子操作,否则可能出现竞争条件,从而破坏了同步互斥机制。此外,还需要注意信号量的初始化以及销毁等问题,否则可能会出现资源泄漏等问题。

通过本次实验,我们不仅实现了生产者-消费者模型,并且深入理解了多线程同步与互斥的概念和方法,同时也锻炼了自己的编程能力和阅读和理解他人代码的能力。在今后的学习和工作中,我们将更好地应用信号量机制和多线程编程,并不断深化对操作系统和计算机原理的理解。

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.hqwc.cn/news/160574.html

如若内容造成侵权/违法违规/事实不符,请联系编程知识网进行投诉反馈email:809451989@qq.com,一经查实,立即删除!

相关文章

Java web(六):FilterListenerAJAX

文章目录 一、Filter1.1 基本介绍1.2 过滤器的执行流程1.3 拦截路径配置1.4 过滤器链1.5 案例 二、Listener三、AJAX3.1 快速入门3.2 Axios异步框架 四、 JSON4.1 JSON基础语法4.2 Fastjson 五、 案例JSONAxiosServlet Java web的三大组件&#xff1a;Servlet、Filter、Listene…

python工具三星路由器远程命令执行漏洞

无人扶我青云志&#xff0c;我自踏雪至山巅&#xff1b;​倘若命中无此运&#xff0c;孤身亦可登昆仑 python工具 漏洞证明&#xff1a; 文笔生疏&#xff0c;措辞浅薄&#xff0c;望各位大佬不吝赐教&#xff0c;万分感谢。 免责声明&#xff1a;由于传播或利用此文所提供的…

Python实现自动化网页操作

1 准备 推荐使用Chrome浏览器 1.1 安装selenium程序包 激活虚拟环境&#xff0c;打开新的Terminal&#xff0c;输入以下代码&#xff1a; python -m pip install selenium 如下图所示&#xff0c;表示安装成功&#xff0c;版本为4.7.2 安装成功 关闭虚拟环境&#xff0c;打…

手动制作Docker容器镜像

文章目录 手动制作Docker容器镜像说明前期准备制作镜像1.启动一个centos系统的容器2.在centos容器中源码安装httpd服务3.基于已经安装好httpd服务的centos容器制作一个httpd镜像4.验证制作出来的镜像的功能5.上传至自己的docker镜像仓库&#xff08;可选&#xff09; 手动制作D…

Apache Doris (五十一): Doris数据缓存

🏡 个人主页:IT贫道_大数据OLAP体系技术栈,Apache Doris,Clickhouse 技术-CSDN博客 🚩 私聊博主:加入大数据技术讨论群聊,获取更多大数据资料。 🔔 博主个人B栈地址:豹哥教你大数据的个人空间-豹哥教你大数据个人主页-哔哩哔哩视频 目录 1.

VScode + opencv + c++ + win配置教程

准备&#xff1a; 1、下载opencv 2、下载MinGw 3、 3、下载CMake 下载完解压放到一个文件夹里面&#xff0c;便于环境管理&#xff0c;文件夹我重命名了&#xff0c;解压出来文件名不一样正常 环境变量配置 C:\Users\wuxulong\cpp_env\MinGw\mingw64\bin C:\Users\wuxulon…

记录离线安装xlwings

有场景需要离线安装xlwings。 环境&#xff1a;win7 64位&#xff0c;python3.8.10-amd64。 首先安装python。 安装需要准备&#xff1a; 其中pywinn32解压如下&#xff1a; 安装python3.8.10&#xff0c;解压各类文件夹。 &#xff08;1&#xff09;首先安装pywin32-306.…

Android性能优化--Perfetto用SQL性能分析

Android性能优化–Perfetto用SQL性能分析 文章目录 Android性能优化--Perfetto用SQL性能分析介绍Perfetto SQL 基础使用 Perfetto SQL 进行性能分析总结 本文首发地址 https://blog.csdn.net/CSqingchen/article/details/134167741 最新更新地址 https://gitee.com/chenjim/che…

IOS渲染流程之提交图层数据至RenderThread进程

大致链路 UIView/CALayer---->CoreAnimation./Core Graphics/Core Image---->GPU Drive-->GPU 图层树/视图树 一个UIView&#xff08;视图&#xff09;对应一个CALayer&#xff08;图层&#xff09;&#xff0c;CALayer对应显示的数据其有个content代表Bitamp&#…

前端下载后端文件流,文件可以下载,但是打不开,显示“文件已损坏”的问题分析与解决方案

目录 场景还原相关代码开发者工具 - 网络请求记录 问题排查定位改bug 总结 场景还原 我在前端使用axios接收后端xlsx表格文件流并下载&#xff0c;xlsx文件能够下载成功&#xff0c;但是打开却显示文件无法打开 相关代码 请求API封装:Content–Type以及responseType经核对均…

CH10_简化条件逻辑

分解条件表达式&#xff08;Decompose Conditional&#xff09; if (!aDate.isBefore(plan.summerStart) && !aDate.isAfter(plan.summerEnd))charge quantity * plan.summerRate; elsecharge quantity * plan.regularRate plan.regularServiceCharge;if (summer())…

Py之auto-gptq:auto-gptq的简介、安装、使用方法之详细攻略

Py之auto-gptq&#xff1a;auto-gptq的简介、安装、使用方法之详细攻略 目录 auto-gptq的简介 1、版本更新历史 2、性能对比 推理速度 困惑度&#xff08;PPL&#xff09; 3、支持的模型 3、支持的评估任务 auto-gptq的安装 auto-gptq的使用方法 1、基础用法 (1)、量…