1.14 互斥与同步

1.思维导图

2.有一个隧道,长1000m,有一辆高铁,每秒100米;有一辆快车,每秒50米;要求模拟这两列火车通过隧道的场景。

1>程序代码:
#include <stdio.h>
#include <string.h>
#include <unistd.h>
#include <stdlib.h>
#include <sys/types.h>
#include <sys/stat.h>
#include <fcntl.h>
#include <pthread.h>
#include <semaphore.h>
#include <wait.h>
#include <signal.h>
#include <sys/socket.h>
#include <arpa/inet.h>
#include <sys/socket.h>
#include <sys/ipc.h>
#include <sys/sem.h>
#include <semaphore.h>
#include <sys/msg.h>
#include <sys/shm.h>
#include <sys/un.h>

typedef struct sockaddr_in addr_in_t;
typedef struct sockaddr addr_t;
typedef struct sockaddr_un addr_un_t;

#define LENGTH 1000  //隧道的长度

typedef struct
{
	const char *name;
	int speed;
	int position;
}Train;

void *simulate_train(void *arg) 
{
    Train *train = (Train *)arg;

    while (train->position < LENGTH) 
	{
        train->position += train->speed;  // 火车前进
        if (train->position > LENGTH)
            train->position = LENGTH;  // 防止超出隧道长度

        printf("%s正在 %d 米处\n", train->name, train->position);
        sleep(1); 
    }

    printf("%s已出隧道\n", train->name);
    return NULL;
}
int main(int argc, const char *argv[])
{

    pthread_t high_speed_thread, fast_train_thread;

    // 初始化两列火车
    Train high_speed_train = {"高铁", 100, 0};
    Train fast_train = {"快车", 50, 0};

    // 创建线程模拟火车运行
    pthread_create(&high_speed_thread, NULL, simulate_train, &high_speed_train);
    pthread_create(&fast_train_thread, NULL, simulate_train, &fast_train);

    // 等待两列火车完成运行
    pthread_join(high_speed_thread, NULL);
    pthread_join(fast_train_thread, NULL);

    printf("两列火车都已出隧道\n");
	return 0;
}
2>运行效果:

3.有一条隧道,长1000m,有一辆高铁,每秒100米;有一辆快车,每秒50米;有一辆慢车,每秒25米;模拟它们通过隧道的场景,要求:高铁最先过隧道,快车其次,慢车最后。

1>程序代码:
#include <stdio.h>
#include <string.h>
#include <unistd.h>
#include <stdlib.h>
#include <sys/types.h>
#include <sys/stat.h>
#include <fcntl.h>
#include <pthread.h>
#include <semaphore.h>
#include <wait.h>
#include <signal.h>
#include <sys/socket.h>
#include <arpa/inet.h>
#include <sys/socket.h>
#include <sys/ipc.h>
#include <sys/sem.h>
#include <semaphore.h>
#include <sys/msg.h>
#include <sys/shm.h>
#include <sys/un.h>

typedef struct sockaddr_in addr_in_t;
typedef struct sockaddr addr_t;
typedef struct sockaddr_un addr_un_t;

#define LENGTH 1000  // 隧道长度

typedef struct 
{
    const char *name;  
    int speed;         
    int position;      
    int order;        //火车顺序 
} Train;

pthread_mutex_t mutex;
pthread_cond_t cond;
int current_order = 1; // 当前允许进入隧道的火车顺序

void *simulate_train(void *arg) 
{
    Train *train = (Train *)arg;

    pthread_mutex_lock(&mutex);
    while (train->order != current_order) {
        pthread_cond_wait(&cond, &mutex);
    }
    pthread_mutex_unlock(&mutex);

    while (train->position < LENGTH) {
        train->position += train->speed;  // 火车前进
        if (train->position > LENGTH) {
            train->position = LENGTH;  // 防止超出隧道长度
        }

        printf("%s正在%d米处\n", train->name, train->position);
        sleep(1);  // 模拟每秒前进
    }

    printf("%s已出隧道\n", train->name);

    pthread_mutex_lock(&mutex);
    current_order++;
    pthread_cond_broadcast(&cond);
    pthread_mutex_unlock(&mutex);

    return NULL;
}

int main(int argc, const char *argv[])
{
	
    pthread_t id1,id2,id3;

    // 初始化三列火车
    Train high_speed_train = {"高铁", 100, 0, 1};
    Train fast_train = {"快车", 50, 0, 2};
    Train slow_train = {"慢车", 25, 0, 3};

    // 创建线程模拟火车运行
    pthread_create(&id1, NULL, simulate_train, &high_speed_train);
    pthread_create(&id2, NULL, simulate_train, &fast_train);
    pthread_create(&id3, NULL, simulate_train, &slow_train);

    // 等待所有线程完成
	pthread_join(id1, NULL);
	pthread_join(id2, NULL);
	pthread_join(id3, NULL);

    printf("所有火车都已出隧道\n");
	return 0;
}
2>运行效果:

4.使用条件变量实现一个生产消费模型(pv模型)。生产者线程:每秒生成2个苹果;消费者线程:每3秒消费5~9个苹果。

1>程序代码:
#include <stdio.h>
#include <string.h>
#include <unistd.h>
#include <stdlib.h>
#include <sys/types.h>
#include <sys/stat.h>
#include <fcntl.h>
#include <pthread.h>
#include <semaphore.h>
#include <wait.h>
#include <signal.h>
#include <sys/socket.h>
#include <arpa/inet.h>
#include <sys/socket.h>
#include <sys/ipc.h>
#include <sys/sem.h>
#include <semaphore.h>
#include <sys/msg.h>
#include <sys/shm.h>
#include <sys/un.h>

typedef struct sockaddr_in addr_in_t;
typedef struct sockaddr addr_t;
typedef struct sockaddr_un addr_un_t;

#define MAX_APPLES 100  //定义仓库最大容量
int apple_count = 0; //当前苹果的数量

//使用条件变量
pthread_mutex_t mutex;
pthread_cond_t cond;

//生产者线程
void* producer(void* arg)
{
	while(1)
	{
		pthread_mutex_lock(&mutex);
		//生产苹果
		if(apple_count+2 <= MAX_APPLES)
		{
			apple_count += 2;
			printf("生产者生产2个苹果,目前苹果总数为:%d\n",apple_count);
		}
		else
		{
			printf("仓库已满,生产者等待生产中...\n");
		}

		//唤醒消费者线程
		pthread_cond_signal(&cond);
		pthread_mutex_unlock(&mutex);

		sleep(1);
	}
	return NULL;
}

//消费者线程
void* consumer(void* arg)
{
	while(1)
	{
		pthread_mutex_lock(&mutex);

		int consumption = rand() % 5 + 5;  //随机消费5~9个苹果

		while(apple_count < consumption)
		{
			printf("消费者想要消费 %d 个苹果,但是只剩 %d 个苹果,等待...\n",consumption,apple_count);
			pthread_cond_wait(&cond,&mutex);  //等待生产者生产
		}
		//消费苹果
		apple_count -= consumption;
		printf("消费者消费 %d 个苹果,剩余苹果: %d个\n",consumption,apple_count);
		pthread_mutex_unlock(&mutex);

		sleep(3);
	}
	return NULL;
}

int main(int argc, const char *argv[])
{
	pthread_t id_producer,id_consumer;

	pthread_create(&id_producer,0,producer,0);
	pthread_create(&id_consumer,0,consumer,0);

	pthread_join(id_producer,NULL);
	pthread_join(id_consumer,NULL);

	return 0;
}

2>运行效果:

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

如若内容造成侵权/违法违规/事实不符,请联系我们进行投诉反馈qq邮箱809451989@qq.com,一经查实,立即删除!

相关文章

研华 PCI-1751 驱动更新导LabVIEW致程序异常

问题描述&#xff1a; 某 LabVIEW 程序长期运行正常&#xff0c;但在使用研华 PCI-1751 数据采集卡运行一段时间后&#xff0c;程序开始出现不正常的行为。具体过程如下&#xff1a; 初始问题&#xff1a; 更换新的 PCI-1751 板卡后&#xff0c;驱动程序被更新&#xff0c;但程…

基于微信小程序的游泳馆管理系统设计与实现(LW+源码+讲解)

专注于大学生项目实战开发,讲解,毕业答疑辅导&#xff0c;欢迎高校老师/同行前辈交流合作✌。 技术范围&#xff1a;SpringBoot、Vue、SSM、HLMT、小程序、Jsp、PHP、Nodejs、Python、爬虫、数据可视化、安卓app、大数据、物联网、机器学习等设计与开发。 主要内容&#xff1a;…

LabVIEW智能水肥一体灌溉控制系统

本文详细介绍了一种基于LabVIEW的智能水肥一体灌溉控制系统的设计与实现。该系统采用模糊控制策略&#xff0c;能够自动调节土壤湿度和肥液浓度&#xff0c;满足不同作物在不同生长阶段的需求&#xff0c;有效提高水肥利用效率&#xff0c;对现代精准农业具有重要的实践和推广价…

ChordCraft荣获重要认可:推动全球音乐教育的数字化革新

2024年12月21日,洛杉矶尔湾市——在今年的文化艺术交流会上,聚集了来自各地的艺术家及社区领袖,共同探讨艺术如何促进全球文化的多样性和教育的普及。 张庭玮(Ting-Wei Chang)女士,University of North Texas音乐艺术博士,是一位享誉国际的单簧管演奏家和音乐教育者。她不仅在…

Public Key Retrieval is not allowed 解决方法

如图&#xff1a;我的报错是Public Key Retrieval is not allowed&#xff0c;我的前后端都能正常加载&#xff0c;但是在请求数据库时就会报错如下&#xff1a; 解决办法&#xff1a; 在 application.yaml 中的数据库设置地方加上allowPublicKeyRetrievaltrue&#xff0c;然后…

unity学习17:unity里的旋转学习,欧拉角,四元数等

目录 1 三维空间里的旋转与欧拉角&#xff0c;四元数 1.1 欧拉角比较符合直观 1.2 四元数 1.3 下面是欧拉角和四元数的一些参考文章 2 关于旋转的这些知识点 2.1 使用euler欧拉角旋转 2.2 使用quaternion四元数,w,x,y,z 2.3 使用quaternion四元数,类 Vector3.zero 这种…

从 Conda 到 Pip-tools:Python 依赖管理全景探索20250113

从 Conda 到 Pip-tools&#xff1a;Python 依赖管理全景探索 引言 在 Python 开发中&#xff0c;依赖管理是一个"常见但复杂"的问题&#xff1a;一次简单的版本冲突可能让团队调试数小时&#xff1b;一次不受控的依赖升级可能让生产环境瘫痪。随着项目规模的增加和…

【容器逃逸实践】挂载/dev方法

0、前置知识 怎么在容器里面执行命令&#xff0c; 有几种方法 # 不进入容器&#xff0c;创建并启动一个新的容器 $ docker run -itd --name ubuntu-test ubuntu /bin/bash # 进入容器&#xff0c;创建并启动一个新的容器 $ docker run -itd --name ubuntu-test ubuntu /bin…

【Linux】进程结束和进程等待

进程的结束 退出码的认识 在我们学习C/C的时候我们通常在进行写main函数时&#xff0c;main函数主体写完后通常会进行写一条语句 " return 0 " &#xff0c;这里的这条语句到底是什么意思呢&#xff1f;&#xff1f; 我们知道当在主函数中调用其他函数或者在其他函…

Apache Hop从入门到精通 第二课 Apache Hop 核心概念/术语

1、apache hop核心概念思维导图 虽然apache hop是kettle的一个分支&#xff0c;但是它的概念和kettle还是有一些区别的&#xff0c;下图是我根据官方文档梳理的appache hop的核心概念思维导图。 2、Tools&#xff08;工具&#xff09; 1&#xff09;Hop Conf Hop Conf 是一个…

28.找出字符串中第一个匹配项的下标【力扣】KMP前缀表 ≈ find() 函数、暴力解法

class Solution { public: //得到前缀表void getNext(int *next,string needle){int j0;for(int i1;i<needle.size();i){while(j>0 && needle[j]!needle[i]) jnext[j-1];//**j>0**>j0是出口if(needle[i]needle[j]) j;next[i]j;//若写入if中&#xff0c;则该…

uniapp 小程序 textarea 层级穿透,聚焦光标位置错误怎么办?

前言 在开发微信小程序时&#xff0c;使用 textarea 组件可能会遇到一些棘手的问题。最近我在使用 uniapp 开发微信小程序时&#xff0c;就遇到了两个非常令人头疼的问题&#xff1a; 层级穿透&#xff1a;由于 textarea 是原生组件&#xff0c;任何元素都无法遮盖住它。当其…

基于深度学习的视觉检测小项目(十三) 资源文件的生成和调用

在使用 PySide6 进行开发时&#xff0c;管理应用程序的资源&#xff08;如图标、图片、字体、样式表、音视频等&#xff09;是一个常见的任务。PySide6 提供了一个工具 pyside6-rcc&#xff0c;它能够将资源文件&#xff08;.qrc&#xff09;编译成 Python 模块&#xff0c;然后…

《计算机网络》课后探研题书面报告_网际校验和算法

网际校验和算法 摘 要 本文旨在研究和实现网际校验和&#xff08;Internet Checksum&#xff09;算法。通过阅读《RFC 1071》文档理解该算法的工作原理&#xff0c;并使用编程语言实现网际校验和的计算过程。本项目将对不同类型的网络报文&#xff08;包括ICMP、TCP、UDP等&a…

【Rust自学】12.6. 使用TDD(测试驱动开发)开发库功能

12.6.0. 写在正文之前 第12章要做一个实例的项目——一个命令行程序。这个程序是一个grep(Global Regular Expression Print)&#xff0c;是一个全局正则搜索和输出的工具。它的功能是在指定的文件中搜索出指定的文字。 这个项目分为这么几步&#xff1a; 接收命令行参数读取…

基于springboot+vue的洪涝灾害应急信息管理系统设计与实现

开发语言&#xff1a;Java框架&#xff1a;springbootJDK版本&#xff1a;JDK1.8服务器&#xff1a;tomcat7数据库&#xff1a;mysql 5.7&#xff08;一定要5.7版本&#xff09;数据库工具&#xff1a;Navicat11开发软件&#xff1a;eclipse/myeclipse/ideaMaven包&#xff1a;…

SpringBoot + 事务钩子函数

一、案例背景 拿支付系统相关的业务来举例。在支付系统中&#xff0c;我们需要记录每个账户的资金流水&#xff08;记录用户A因为哪个操作扣了钱&#xff0c;因为哪个操作加了钱&#xff09;&#xff0c;这样我们才能对每个账户的账做到心中有数&#xff0c;对于支付系统而言&…

基于微信小程序的智能停车场管理系统设计与实现(LW+源码+讲解)

专注于大学生项目实战开发,讲解,毕业答疑辅导&#xff0c;欢迎高校老师/同行前辈交流合作✌。 技术范围&#xff1a;SpringBoot、Vue、SSM、HLMT、小程序、Jsp、PHP、Nodejs、Python、爬虫、数据可视化、安卓app、大数据、物联网、机器学习等设计与开发。 主要内容&#xff1a;…

接上一主题,实现QtByteArray任意进制字符串转为十进制数

函数&#xff1a; /// <summary>/// n进制字符串转为十进制数&#xff0c;snDefine的长度最小为二进制数。/// 例子&#xff1a;/// _pn(_Math::strNToInt(_t("1010"), _t("01")));/// _pn(_Math::strNToInt(_t("-1010"), _t("0123…

小游戏前端地区获取

目前前端获取除了太平洋&#xff0c;没有其它的了。 //在JS中都是使用的UTF-8&#xff0c;然而requst请求后显示GBK却是乱码&#xff0c;对传入的GBK字符串&#xff0c;要用数据流接收&#xff0c;responseType: "arraybuffer" tt.request({url: "https://whoi…