简单的喷淋实验(2):(1)根据土壤湿度自动控制喷淋开关;(2)根据光照强度控制风扇以及灯的开关---嵌入式实训

news2024/11/17 13:20:18

目录

简单的喷淋实验(2):

        (1)根据土壤湿度自动控制喷淋开关;

        (2)根据光照强度控制风扇以及灯的开关---嵌入式实训

任务2:

具体过程:

所用的头文件:

data_global.h

mqtt.h

主程序:mian.c

运行结果:

运行过程视频:

上述程序存在问题:

初步破局:

继续探讨:


简单的喷淋实验(2):

        (1)根据土壤湿度自动控制喷淋开关;

        (2)根据光照强度控制风扇以及灯的开关---嵌入式实训

任务2

在所给的 irrigate-1 文件夹中创建一个main.c 完成以下内容:

(1)根据土壤湿度自动控制喷淋开关

(2)根据光照强度控制风扇以及灯的开关

参考:

#include <stdio.h>
#include <unistd.h>
#include "mqtt.h"
#include "parse_config.h"

#define SUB_TOPIC  "1703161172612/AIOTSIM2APP"   //定阅的主题
#define PUB_TOPIC  "1703161172612/APP2AIOTSIM"  //发布主题

#define IRRIGATED_ON "{\"irrigated\":true}"
#define IRRIGATED_OFF "{\"irrigated\":false}"

#define FAN_ON		"{\"fan\":true}"
#define FAN_OFF		"{\"fan\":false}"

#define LAMP_ON		"{\"lamp\":true}"
#define LAMP_OFF		"{\"lamp\":false}"

#define ALARM_ON		"{\"alarm\":true}"
#define ALARM_OFF		"{\"alarm\":false}"

int main(int argc, const char *argv[])
{
	ENV msg_env={};
	//1.初始化mqtt协议
	if(mqtt_init()!=0)
	{
		printf("mqtt init err.\n");
		return -1;
	}
	//订阅别人发布的消息
	if(mqtt_subscribe(SUB_TOPIC) < 0)
	{
		printf("sub err.\n");
		return -1;
	}
	//循环获取温湿度
	//当大于阈值关闭灌溉,小于就打开
	while(1)
	{
		sleep(1);
		//获取值
		msg_env=get_virtual_env();

		if(msg_env.ill < 20000)
		{
			mqtt_publish(PUB_TOPIC,FAN_OFF);
			mqtt_publish(PUB_TOPIC,LAMP_ON);
		}else if(msg_env.ill > 50000)
		{
			mqtt_publish(PUB_TOPIC,FAN_ON);
			mqtt_publish(PUB_TOPIC,LAMP_OFF);
		}
		printf("ill:%f\n",msg_env.ill);


		if(msg_env.soil < 30)
		{
			mqtt_publish(PUB_TOPIC,IRRIGATED_ON);
		}else if(msg_env.soil > 50)
		{
			mqtt_publish(PUB_TOPIC,IRRIGATED_OFF);
		}
		printf("soilhum:%f\n",msg_env.soil);

		// if(msg_env.infrared == 1)
		// {
		// 	mqtt_publish(PUB_TOPIC,ALARM_ON);
		// }else {
		// 	mqtt_publish(PUB_TOPIC,ALARM_OFF);
		// }
		// printf("infrared:%d\n",msg_env.infrared);

	}
	exit_mqtt();
	return 0;
}

具体过程:

所用的头文件:
data_global.h
#ifndef __DATA_GLOBAL__H__
#define __DATA_GLOBAL__H__

#include <stdio.h>
#include <string.h>
#include <stdlib.h>
#include <errno.h>
#include <unistd.h>
#include <sys/types.h>
#include <sys/socket.h>
#include <arpa/inet.h>
#include <netinet/in.h>
#include <time.h>
#include <termios.h>
#include <signal.h>
#include <sys/stat.h>
#include <fcntl.h>
#include <pthread.h>
#include <stdbool.h>
struct env_info
{
	float soil;  //土壤湿度
	float light; //光照强度
	float temp;   //空气温度
	uint8_t gas;    //有害气体
};

extern struct env_info env_msg;

//设备编号
#define FAN  0x00
#define BEEP 0x10
#define LED  0x20
#define PUMP 0X30

#define DATA_ARRIVE SIGUSR1 //数据到达信号


//订阅、发布主题
#define ENV_PUB_TOPIC "FS_VRJJ/control"

//虚拟仿真硬件协议
#define LAMP_ON    "{\"lamp\":true}"
#define LAMP_OFF   "{\"lamp\":false}"

#define ALARM_ON   "{\"alarm\":true}"
#define ALARM_OFF  "{\"alarm\":false}"

#define SUNSHADE_FOR "{\"sunshade\":\"forward\"}"
#define SUNSHADE_REV	"{\"sunshade\":\"reverse\"}"
#define SUNSHADE_STOP	"{\"sunshade\":\"stop\"}"

#define VIR_FAN_ON	"{\"fan\":true}"
#define VIR_FAN_OFF "{\"fan\":false}"

#define IRRIGATED_OFF "{\"irrigated\":false}"
#define IRRIGATED_ON "{\"irrigated\":true}"
#endif
mqtt.h
#ifndef __MQTT_SMART_H_
#define __MQTT_SMART_H_


typedef struct env
{
	float soil;//土壤湿度
	float ill;//光照
	int smog;//烟雾
	int infrared;//人体红外
}ENV;
int mqtt_init();
void exit_mqtt();
int mqtt_subscribe(const char*topic);
int mqtt_publish(const char *topic, char *msg);
ENV get_virtual_env();

#endif
主程序:mian.c
#include<stdio.h>
#include"mqtt.h"
#include<unistd.h>
#include"data_global.h"
 
#define subscribe "1703503856299/AIOTSIM2APP"
#define publish "1703503856299/APP2AIOTSIM"
int main(int argc, char *argv[]){
    //1-连接服务器
    mqtt_init();
 
    //2-订阅元宇宙平台主题,获得数据串
        //通过目标节点的发布主题,才能的得到发布的内容
    mqtt_subscribe(subscribe);

 
    //4.循环获取数据,下发控制指令
    while (1){
        sleep(1);
        ENV env= get_virtual_env();
        if (env.soil>60){
            mqtt_publish(publish, IRRIGATED_OFF);
            printf("关闭喷淋。。。。\n");
        }
        else if (env.soil<30){
            mqtt_publish(publish, IRRIGATED_ON);
            printf("打开喷淋\n");
        }

        printf("当前土壤湿度:%.2f\n", env.soil);

        if (env.ill>27000)
        {
            mqtt_publish(publish, VIR_FAN_ON);
            mqtt_publish(publish,  LAMP_OFF);
            printf("打开风扇,关闭灯。。。。\n");
        }
        else if (env.ill<25000)
        {
            mqtt_publish(publish,  VIR_FAN_OFF);
            mqtt_publish(publish,  LAMP_ON);
            printf("关闭风扇,打开灯。。。。。。\n");
        }
        
        sleep(1);
        printf("当前光照强度:%.2f\n", env.ill);
        printf("++++++++++++++++++++++++++++\n");
    }
    exit_mqtt();
    return 0;
}
运行结果:

元宇宙未运行时:

元宇宙运行后:

运行过程视频:

嵌入式实训2023-12-25 20-19-53


上述程序存在问题:

初步破局:

在元宇宙实验平台还没开始运行时,各种数据都是0,就会导致程序通过if、else if判断语句来控制各种机器运作,这是不正确的。为了避免这种情况,可以添加一些额外的判断来解决这个问题。

首先,我们可以在while循环之前添加一个延时等待,让实验平台有足够的时间来获取和发送数据。例如,我们可以使用sleep函数来等待5秒钟:

sleep(5); // 等待5秒钟,让实验平台有足够的时间来获取和发送数据

然后,我们可以在if、else if判断语句之前添加一个判断,检查所需的数据是否已经被正确地获取。例如,我们可以检查土壤湿度是否为0来确定是否成功获取了土壤湿度数据:

ENV env= get_virtual_env();
if (env.soil == 0) {
    printf("未成功获取到土壤湿度数据,等待下一次获取...\n");
    sleep(1);
    continue; // 跳过本次循环,等待下一次循环
}

// 在此之后添加if、else if判断语句进行控制

 同样,我们可以添加类似的判断来检查光照强度等数据是否已经被正确获取。这样做可以避免在数据未准备好时误操作机器,保证程序的正确性。

完整代码:

#include<stdio.h>
#include"mqtt.h"
#include<unistd.h>
#include"data_global.h"
 
#define subscribe "1703503856299/AIOTSIM2APP"
#define publish "1703503856299/APP2AIOTSIM"
int main(int argc, char *argv[]){
    //1-连接服务器
    mqtt_init();
 
    //2-订阅元宇宙平台主题,获得数据串
        //通过目标节点的发布主题,才能的得到发布的内容
    mqtt_subscribe(subscribe);

    //3.等待数据准备就绪
    printf("等待数据准备就绪...\n");
    sleep(5); // 等待5秒钟,让实验平台有足够的时间来获取和发送数据

    //4.循环获取数据,下发控制指令
    while (1){
        ENV env= get_virtual_env();
        if (env.soil == 0) {
            printf("未成功获取到土壤湿度数据,等待下一次获取...\n");
            sleep(1);
            continue; // 跳过本次循环,等待下一次循环
        }

        if (env.soil>60){
            mqtt_publish(publish, IRRIGATED_OFF);
            printf("关闭喷淋。。。。\n");
        }
        else if (env.soil<30){
            mqtt_publish(publish, IRRIGATED_ON);
            printf("打开喷淋\n");
        }

        printf("当前土壤湿度:%.2f\n", env.soil);

        if (env.ill == 0) {
            printf("未成功获取到光照强度数据,等待下一次获取...\n");
            sleep(1);
            continue; // 跳过本次循环,等待下一次循环
        }

        if (env.ill>27000)
        {
            mqtt_publish(publish, VIR_FAN_ON);
            mqtt_publish(publish,  LAMP_OFF);
            printf("打开风扇,关闭灯。。。。\n");
        }
        else if (env.ill<25000)
        {
            mqtt_publish(publish,  VIR_FAN_OFF);
            mqtt_publish(publish,  LAMP_ON);
            printf("关闭风扇,打开灯。。。。。。\n");
        }
        
        printf("当前光照强度:%.2f\n", env.ill);
        printf("++++++++++++++++++++++++++++\n");
        sleep(1);
    }

    exit_mqtt();
    return 0;
}

继续探讨:

还是有点问题,如果等待5秒后,实验平台运行了,但是土壤湿度和光照强度又恰好是0呢?这样是没有错误的呀

上述提出了一个很好的问题。确实,在等待5秒后,如果土壤湿度和光照强度仍然是0,那么程序就会继续执行,而不会等待数据准备就绪。为了解决这个问题,可以使用一个循环来判断数据是否已经准备就绪,并设置一个最大等待时间。

下面是修改后的代码示例:

#include<stdio.h>
#include"mqtt.h"
#include<unistd.h>
#include"data_global.h"
 
#define subscribe "1703503856299/AIOTSIM2APP"
#define publish "1703503856299/APP2AIOTSIM"
int main(int argc, char *argv[]){
    //1.连接服务器
    mqtt_init();
 
    //2.订阅元宇宙平台主题,获得数据串
    //通过目标节点的发布主题,才能的得到发布的内容
    mqtt_subscribe(subscribe);

    //3.等待数据准备就绪
    printf("等待数据准备就绪...\n");
    int max_wait_time = 10; // 最大等待时间为10秒
    int wait_time = 0; // 已等待的时间
    ENV env;
    while (1){
        env= get_virtual_env();
        if (env.soil != 0 && env.ill != 0) {
            break; // 数据已准备就绪,跳出循环
        }

        sleep(1);
        wait_time++;
        if(wait_time >= max_wait_time){
            printf("超过最大等待时间,未成功获取到数据!\n");
            exit_mqtt();
            return 0;
        }
    }

    //4.循环获取数据,下发控制指令
    while (1){
        if (env.soil>60){
            mqtt_publish(publish, IRRIGATED_OFF);
            printf("关闭喷淋。。。。\n");
        }
        else if (env.soil<30){
            mqtt_publish(publish, IRRIGATED_ON);
            printf("打开喷淋\n");
        }

        printf("当前土壤湿度:%.2f\n", env.soil);

        if (env.ill>27000)
        {
            mqtt_publish(publish, VIR_FAN_ON);
            mqtt_publish(publish,  LAMP_OFF);
            printf("打开风扇,关闭灯。。。。\n");
        }
        else if (env.ill<25000)
        {
            mqtt_publish(publish,  VIR_FAN_OFF);
            mqtt_publish(publish,  LAMP_ON);
            printf("关闭风扇,打开灯。。。。。。\n");
        }
        
        printf("当前光照强度:%.2f\n", env.ill);
        printf("++++++++++++++++++++++++++++\n");
        sleep(1);
    }

    exit_mqtt();
    return 0;
}

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

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈,一经查实,立即删除!

相关文章

BDD - Python Behave Retry 机制

BDD - Python Behave Retry 机制 引言Behave RetryBehave Retry 应用feature 文件创建 step 文件Retry运行 Behave 并生成 rerun 文件重新运行失败的场景 引言 在日常运行测试用例&#xff0c;有时因为环境不稳定造成一些测试用例跑失败了&#xff0c;如果能将这些失败的测试用…

少走弯路:单片机使用点阵字体通过像素化的正确获取

要在单片机内自由显示文字&#xff0c;必须准备相应的字库。之前也发文介绍过&#xff1a; 在esp32(esp8266) 提供软字库显示中文的解决方案_esp32中文字库-CSDN博客 包括已经开源的项目&#xff1a; https://github.com/StarCompute/tftziku 这种字体获取思路是&#xff1a…

test mock-01-什么是 mock? Mockito/EasyMock/PowerMock/JMockit/Spock mock 框架对比

拓展阅读 test 之 jmockit-01-overview jmockit-01-test 之 jmockit 入门使用案例 mockito-01-overview mockito 简介及入门使用 PowerMock Mock Server ChaosBlade-01-测试混沌工程平台整体介绍 jvm-sandbox 入门简介 单元测试中的 mock 单元测试是一种验证代码单元&…

echart实现自定义图例文字颜色

1.效果图 2.html <div class"biao" id"biao1"></div> 2.js 关键&#xff1a; color: [#2db7f5, #ff6600, #921AFF, #c32441, #FF00FF, #FF8EFF, #53FF53, #F9F900, #00FFFF],//关键:自定义图例文字颜色在legend中添加data,将数据处理成如下…

git远程操作,推送【push】,拉取【pull】,忽略特殊文件,配置别名,标签管理

文章目录 前言&#xff1a;新建远程仓库克隆推送【push】拉取【pull】 配置git忽略特殊文件给命令配置别名 标签管理理解标签创建标签操作标签 前言&#xff1a; 大家如果没有看过前几章git的基础操作的话&#xff0c;推荐先看一下&#xff0c;看完再来看这个远程操作&#xf…

查看ios app运行日志

摘要 本文介绍了一款名为克魔助手的iOS应用日志查看工具&#xff0c;该工具可以方便地查看iPhone设备上应用和系统运行时的实时日志和奔溃日志。同时还提供了奔溃日志分析查看模块&#xff0c;可以对苹果奔溃日志进行符号化、格式化和分析&#xff0c;极大地简化了开发者的调试…

单集群400TB,OceanBase稳定支撑快手核心业务场景

一款日均超过千万人访问的短视频 App 快手&#xff0c;面对高并发流量如何及时有效地处理用户请求&#xff1f;通过在后端配置多套 MySQL 集群来支撑高流量访问&#xff0c;以解决大数据量存储和性能问题&#xff0c;这种传统的 MySQL 分库分表方案有何问题&#xff1f;快手对分…

个人游戏启动器 | 游戏数据库 playnite 折腾记录

环境&#xff1a;Windows 11 问题&#xff1a;使用平板串联PC游戏后&#xff0c;需要一个本地的PC启动器 解决办法&#xff1a;使用playnite搭配插件 背景&#xff1a;我是个单机游戏爱好者&#xff0c;因为某些原因&#xff0c;需要串流游玩&#xff0c;需要一个方便手柄操作的…

安全运维是做什么的,主要工作内容是什么

安全运维&#xff0c;简称SecOps&#xff0c;是一种集成安全措施和流程到信息技术运维的实践。它的目的是确保在日常运维活动中&#xff0c;如网络管理、系统维护、软件更新等&#xff0c;均考虑并融入安全策略。安全运维的核心是实现安全和运维团队的密切协作&#xff0c;以快…

鸿蒙系列--组件介绍之其他基础组件(上)

上回介绍了基础组件中最常用的组件常用的基础组件&#xff0c;接下来还有其他基础组件 一、Blank 描述&#xff1a;空白填充组件 功能&#xff1a;在容器主轴方向上&#xff0c;具有自动填充容器空余部分的能力。只有当父组件为Row/Column时生效 子组件&#xff1a;无 Blan…

Echarts使用,Echarts图表自适应窗口大小

Echarts官方文档 1.下载Echarts 项目打打开终端直接通过命令 npm install echarts --save 下载完成后在项目package.json查看。 2.使用Echarts 引入方式有两种全局引入和局部引入 全局引入直接在项目main.js引入放到vue原型上。 import * as echarts from echarts Vue.pr…

《Linux C/C++服务器开发实践》:深入探索网络编程的基础知识与实用技术

&#x1f3a5; 屿小夏 &#xff1a; 个人主页 &#x1f525;个人专栏 &#xff1a; 书籍推荐 &#x1f304; 莫道桑榆晚&#xff0c;为霞尚满天&#xff01; 文章目录 &#x1f4d1;前言一. 构建高性能Linux C/C服务器1.1 优化服务器性能1.2 处理并发和并行性1.3 高效管理内存1…

【新资讯】《网络安全事件报告管理办法(征求意见稿)》正在公开征求意见

近年来网络安全事故频发&#xff0c;造成了不少损失和危害。为了减少网络安全事故的发生&#xff0c;规范网络安全事件的报告&#xff0c;国家互联网信息办公室根据《中华人民共和国网络安全法》等法律法规起草了《网络安全事件报告管理办法&#xff08;征求意见稿&#xff09;…

【Linux基础】5. 磁盘管理

文章目录 【 1. 查看磁盘空间 】1.1 df 查看空间利用大小1.2 du 查看目录所占空间大小 【 2. 打包、压缩 】2.1 tar -cvf 打包2.2 gzip 压缩 【 3. 解压缩、解包 】3.1 gunzip 解压缩3.2 tar -xvf 解包 【 1. 查看磁盘空间 】 1.1 df 查看空间利用大小 作用 查看整个文件系统…

keras 人工智能之VGGNet神经网络的图片识别

VGG16结构图 上期文章我们分享了如何使用VGGNet CNN网络结构搭建一个图片识别网络,以及训练了神经网络模型,利用上期训练好的神经模型,可以进行我们的图片识别 图片识别结果 导入第三方库 from keras.preprocessing.image import img_to_array from keras.models import …

企业级实战项目:基于 pycaret 自动化预测公司是否破产

本文系数据挖掘实战系列文章&#xff0c;我跟大家分享一个数据挖掘实战&#xff0c;与以往的数据实战不同的是&#xff0c;用自动机器学习方法完成模型构建与调优部分工作&#xff0c;深入理解由此带来的便利与效果。 1. Introduction 本文是一篇数据挖掘实战案例&#xff0c;…

美国某金融公司遭遇网络攻击,130 万民众受影响

The Record 网站披露&#xff0c;美国最大的产权保险公司富达国民金融&#xff08;Fidelity National Financial&#xff08;"FNF"&#xff09;&#xff09;子公司向所在州监管机构报告了一起数据泄露事件&#xff0c;并指出有 1316938 人的数据信息被入侵其母公司的…

普中STM32-PZ6806L开发板(烧录方式)

前言 有两种方式, 串口烧录和STLink方式烧录;串口烧录 步骤 开发板USB转串口CH340驱动板接线到USB连接PC使用自带工具普中自动下载软件.exe烧录程序到开发板 ST Link方式 这种方式需要另外进行供电&#xff0c; 我买的如下&#xff0c;当年用于调试STM8的&#xff0c;也可…

uniapp中两个app互相跳转

例如,appA需要跳转到appB里面 第一步配置,android不用配置的&#xff0c;主要是配置ios的白名单 appB中 appA中 第二步代码 handleJump() {if (plus.runtime.isApplicationExist({pname: com., //安卓包名action: https://a //ios地址})) {if (plus.os.name Android) {pl…

什么是数据实时同步?对企业有什么重要性?

在当前的信息时代&#xff0c;数据的重要性已经超越了企业的资产范畴&#xff0c;成为推动创新和发展的核心动力。数据质量、完整性和可用性直接关系到企业的决策、运营和竞争力&#xff0c;因此&#xff0c;如何高效地管理和利用数据已经成为企业面临的重要挑战和机遇。 数据同…