使用 `millis()` 函数在 Arduino 编程中实现非阻塞延时(水泵/继电器不受控制为例)

在 Arduino 编程中,delay() 函数是一个常见的工具,用于创建代码执行的延时。然而,delay() 函数的一个显著缺点是它会阻塞代码的执行。这意味着当 delay() 函数运行时,Arduino 将暂停其他所有的操作,直到延时结束。这种阻塞行为在某些简单的项目中可能是可接受的,但在需要同时运行多个任务的复杂项目中,这种方式会带来严重的问题。

例如,在一个需要同时读取传感器数据、控制输出设备和处理用户输入的项目中,使用 delay() 函数会导致其他任务无法按时执行,影响整个系统的响应能力和效率。为了解决这个问题,我们可以使用 millis() 函数来实现非阻塞延时。

millis() 函数返回自 Arduino 开机以来经过的毫秒数。这使得我们可以通过记录特定时刻的时间戳,并在后续的代码中检查是否已经经过了预定的时间,从而实现非阻塞延时。这种方法的核心思想是持续检查当前时间与记录的时间之间的差值,而不是暂停代码执行。

实现非阻塞延时的步骤

  1. 记录初始时间:在执行延时操作之前,使用 millis() 函数记录当前时间。
  2. 检查时间差:在循环中持续检查当前时间与初始时间的差值,判断是否已经经过了预定的延时时间。
  3. 继续其他任务:在等待时间达到的过程中,允许代码继续执行其他任务。

以下是一个简单的例子,演示如何使用 millis() 函数实现非阻塞延时:

unsigned long previousMillis = 0;  // 记录上一次更新的时间
const long interval = 1000;        // 延时间隔(毫秒)void setup() {Serial.begin(9600);
}void loop() {unsigned long currentMillis = millis();  // 获取当前时间// 检查是否已经到达预定时间间隔if (currentMillis - previousMillis >= interval) {previousMillis = currentMillis;  // 更新记录的时间// 执行需要延时的操作Serial.println("1秒已过");}// 执行其他任务// 例如,读取传感器数据或处理用户输入int sensorValue = analogRead(A0);Serial.println(sensorValue);
}

在这个例子中,程序每隔1秒钟执行一次特定的任务,同时在等待时间到达的过程中继续执行其他任务,如读取传感器数据。通过这种方式,我们避免了 delay() 函数带来的阻塞问题。

优势

使用 millis() 函数实现非阻塞延时有以下几个主要优势:

  1. 提高响应能力:代码可以在等待时间到达的过程中继续运行其他任务,提高了系统的响应速度。
  2. 多任务处理:允许多个任务并行运行,而不是因为一个延时操作而暂停整个系统。
  3. 更灵活的时间管理:可以轻松实现不同任务的不同延时要求,而不需要嵌套多个 delay() 调用。

应用场景

在实际应用中,非阻塞延时的使用场景非常广泛。典型的应用包括:

  • 实时数据采集:在传感器数据采集中,定期读取数据而不影响其他处理逻辑。
  • LED 控制:在 LED 闪烁或其他定时控制中,同时处理按钮输入和状态显示。
  • 机器人控制:在机器人项目中,处理多个传感器输入和执行动作,而不会因为单一的延时操作而影响整体协调。

总之,使用 millis() 函数来实现非阻塞延时是提升 Arduino 项目效率和响应能力的有效方法。通过理解和应用这种技术,开发者可以设计出更为复杂和功能强大的嵌入式系统。

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

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

相关文章

小工具开发

因不太喜欢重复性工作,为了提高日常工作效率,在业余时间开发一些小工具用于帮助自己“偷懒”。 小工具功能: 1、Hightec编译的hex文件,与多模式标定hex文件合成 2、Bootloader文件,Hightec编译的hex文件,与…

Oracle 系列数据库使用 listagg去重,删除重复数据的几种方法

listagg聚合之后很多重复数据,下面是解决重复数据问题 案例表 create table "dept_tag_info" ( "tag_id" bigint not null, "tag_code" varchar(200), "tag_name" varchar(500), "tag_level" varchar(200), &…

java-接口 2

### 7. 接口的设计原则 #### 7.1 接口隔离原则(ISP) 接口隔离原则(Interface Segregation Principle, ISP)建议将大的接口分解为多个小接口,每个接口只包含客户所需的方法。这使得实现类 只需实现其真正需要的接口&…

KindleUnpack - Python解压Amazon / Kindlegen生成的电子书

文章目录 关于 KindleUnpack使用选项 关于 KindleUnpack github : https://github.com/kevinhendricks/KindleUnpack KindleUnpack 是基于python的软件来解压Amazon / Kindlegen生成的电子书 KindleUnpack将非drm Kindle/MobiPocket电子书解压到其组件中 根据正在处理的Kindl…

Android Studio新增功能:Device Streaming

今天将Android Studio升级到2023.3.1 Patch2。发现新增了Device Streaming功能。支持远程使用Google的物理设备调试程序。这样可以方便地在真实设备上测试自己的APP。这对于手头没有Google设备的开发者而言,确实方便很多。该功能目前处于测试阶段,在2025…

交易中的群体行为特征和决策模型

本文基于人的行为和心理特征,归纳出交易中群体的行为决策模型,并基于这个模型,分析股价波浪运行背后的逻辑,以及投机情绪的周期变化规律,以此指导交易,分析潜在的风险和机会,寻找并等待高性价比…

system与excel族函数区别

1.system #include<stdlib.h> int system(const char *command); comand是命令的路径&#xff0c;一般我们用绝对路径 system函数会创建新的进程&#xff0c;新的进程执行完返回原来的进程&#xff0c;原来的进程则继续执行后面的代码段。 如我们创建一个sys.cpp文件…

使用pip2pi和nginx搭建私有pip镜像源方法

在内网环境下部署python开发环境&#xff0c;安装python第三方库比较麻烦&#xff0c;特别是安装需要多个依赖的库。一种比较好的解决方案是搭建一个本地的私有pip镜像源&#xff0c;有多个方案可以选择&#xff0c;比如pypiserver、pip2pi等&#xff0c;本文介绍使用python的p…

Python求子数组和的所有元素(附Demo)

目录 前言1. 暴力求解2. 前缀和哈希表3. 滑动窗口 前言 工作需要&#xff0c;对应需要优化查找子数组和等于特定值的算法 对应的算法推荐&#xff1a;子数组相关题目 以下算法主要针对Python 1. 暴力求解 双重循环时间复杂度为 O(n2) def subarrays_with_sum_equal_k(num…

PostgreSQL如何使修改的参数生效

PostgreSQL如何使修改的参数生效 在 PostgreSQL 中&#xff0c;配置参数的更改往往需要不同的方式来使其生效。根据参数的不同&#xff0c;它们的生效方式可能有所区别&#xff0c;例如&#xff1a; 立即生效&#xff1a;某些参数可以通过会话级别的设置即时生效&#xff0c;…

HTML的常用标签

HTML&#xff08;补&#xff09; CSS选择器 元素选择器&#xff1a;指定一个标签给这个标签设置一个默认的样式。设置的样式对所有相同的标签都有用。 id选择器&#xff1a;我们可以给标签指定一个唯一的id&#xff0c;然后根据id可以在style标签中设置对应标签的样式元素。设…

【仿真建模-anylogic】FlowchartBlock原理解析

Author&#xff1a;赵志乾 Date&#xff1a;2024-06-17 Declaration&#xff1a;All Right Reserved&#xff01;&#xff01;&#xff01; 1. 类图 2. 原理解析 2.1 核心函数 函数功能FlowchartBlock(Engine engine ,Agent owner, AgentList population )构造函数&#xff…

springboot-自定义properties文件

在springboot中&#xff0c;如果我们想加载外部的配置文件&#xff0c;但是又不想与其他的配置文件产生明显的耦合&#xff0c;那么我们可以把这些配置文件&#xff0c;单独弄成一个独立的配置文件&#xff0c;比如下面的配置文件&#xff0c;我们想把这些配置移动到user.prope…

CountDownLatch案例

CountDownLatch&#xff08;倒计时门闩&#xff09;是Java并发编程中的一个同步工具&#xff0c;其作用是允许一个或多个线程等待其他线程完成操作后再继续执行。具体来说&#xff0c;它通常用于以下场景&#xff1a; 等待其他线程完成某项操作&#xff1a; 一个或多个线程需要…

element-vue3-admin用router.push跳转新页面并刷新新页面

element-vue3-admin用router.push跳转新页面并刷新新页面 方法一&#xff1a;使用key属性强制刷新1.首先在invex.vue页面加上router-view标签对2.然后在add.vue页面加入如下代码 方法二&#xff1a;使用location.reload()在add.vue页面加入location.reload()强制浏览器刷新整个…

Day 24:100301. 构成整天的下标对数目II

Leetcode 100301. 构成整天的下标对数目II 给你一个整数数组 hours&#xff0c;表示以 **小时 **为单位的时间&#xff0c;返回一个整数&#xff0c;表示满足 i < j 且 hours[i] hours[j] 构成 **整天 **的下标对 i, j 的数目。 **整天 **定义为时间持续时间是 24 小时的 *…

在Spring Cloud项目中集成Springdoc OpenAPI生成OpenAPI 3文档的详细解析

在Spring Cloud项目中集成Springdoc OpenAPI生成OpenAPI 3文档的详细解析 在Spring Cloud项目中生成OpenAPI 3文档&#xff0c;可以使用Springdoc OpenAPI。Springdoc OpenAPI提供了一种简单的方法来生成符合OpenAPI 3规范的API文档。以下是详细的步骤和解析&#xff0c;展示如…

助力樱桃智能自动化采摘,基于YOLOv5全系列【n/s/m/l/x】参数模型开发构建果园种植采摘场景下樱桃成熟度智能检测识别系统

随着科技的飞速发展&#xff0c;人工智能&#xff08;AI&#xff09;技术已经渗透到我们生活的方方面面&#xff0c;从智能家居到自动驾驶&#xff0c;再到医疗健康&#xff0c;其影响力无处不在。然而&#xff0c;当我们把目光转向中国的农业领域时&#xff0c;一个令人惊讶的…

虾皮平台API:获取商品买家评论数据

一、接口核心功能 在电商领域&#xff0c;买家评论对于商品的销售和商家的口碑至关重要。虾皮作为东南亚地区知名的电商平台&#xff0c;为商家提供了丰富的商品买家评论数据。为了方便商家获取这些数据&#xff0c;我们的API接口服务其核心功能就是获取商品买家评论数据信息。…

2024年6月17日--6月23日(渲染+ue独立游戏,)

工作要继续做渲染了&#xff0c;所以还是要把渲染搞一搞。 试过重点放在独立游戏上&#xff0c;有个indienova独立游戏团队是全职的&#xff0c;由于他们干了几个月&#xff0c;节奏暂时跟不上&#xff0c;紧张焦虑了。五一时也有点自暴自弃了&#xff0c;实在没必要&#xff…