蓝桥杯单片机快速开发笔记——特训4 24C02—E2PROM存储按键触发次数

一、原理分析

        HC573/HC138:http://t.csdnimg.cn/W0a0U

        数码管:http://t.csdnimg.cn/kfm9Y

        AT24C02 E2PROM:http://t.csdnimg.cn/DI8XH

        独立键盘:http://t.csdnimg.cn/YPInc

二、题目要求

        

在CT107D单片机综合训练平台上,新建工程并以I/O模式编写代码,实现以下功能:

  1. 移植IIC总线的底层驱动代码文件到工程中。
  2. 将J5的23脚短接,设置S4、S5和S6为独立按键。
  3. 使用24C02存储器的0x00、0x01和0x02地址单元分别记录S4、S5和S6按下的次数。
  4. 系统上电后,首先从24C02存储器的0x00、0x01和0x02地址单元读取数据,然后按照S4、S5和S6的顺序从左到右依次在数码管上显示,数字之间用“-”分隔。
  5. 每次按下S4、S5或S6按键,对应的历史按下次数加1,累计值超过13时自动清零。
  6. 将最新的按键按下次数写入24C02的相应单元,并在数码管上刷新显示。

三、代码示例

#include "stc15.h"void hc573(unsigned char channel, unsigned char dat)
{P2 = (P2 & 0x1f) | 0x00;P0 = dat;switch(channel){case 4:P2 = (P2 & 0x1f) | 0x80;   //LEDbreak;case 5:P2 = (P2 & 0x1f) | 0xa0;   //蜂鸣器和继电器break;case 6:P2 = (P2 & 0x1f) | 0xc0;   //数码管位选break;case 7:P2 = (P2 & 0x1f) | 0xe0;   //数码管段选break;}P2 = (P2 & 0x1f) | 0x00;
}void delay_smg(unsigned int t)
{while(t--);
}void delay_key(unsigned int t)
{while(t--);
}void delay_24c02(unsigned int t)
{while(t--);
}#define TSMG 500unsigned char num1 = 0;   //计数S4
unsigned char num2 = 0;		//计数S5
unsigned char num3 = 0;		//计数S6code unsigned char Seg_Table[] = 
{0xc0, //00xf9, //10xa4, //20xb0, //30x99, //40x92, //50x82, //60xf8, //70x80, //80x90, //90x88, //A0x83, //b0xc6, //C0xa1, //d0x86, //E0x8e //F
};void smg_all(unsigned char dat)
{hc573(6,0xff);hc573(7,dat);
}void smg_bit(unsigned char pos, unsigned char dat)
{hc573(6,0x01 << pos);hc573(7,dat);delay_smg(TSMG);hc573(6,0x01 << pos);hc573(7,0xff);         //消影
}void smg_dispaly()
{smg_bit(0, Seg_Table[num1 / 10]);smg_bit(1, Seg_Table[num1 % 10]);smg_bit(2, 0xbf);smg_bit(3, Seg_Table[num2 / 10]);smg_bit(4, Seg_Table[num2 % 10]);smg_bit(5, 0xbf);smg_bit(6, Seg_Table[num3 / 10]);smg_bit(7, Seg_Table[num3 % 10]);
}#define TKEY 200
#define CKEY 1300sbit s4 = P3^3;
sbit s5 = P3^2;
sbit s6 = P3^1;void key()
{if(s4 == 0)         //判断是否按下{delay_key(TKEY);  //消抖if(s4 == 0)       //再次判断{num1++;if(num1 > 13){num1 = 0;}write_24c02(0x00, num1);delay_24c02(CKEY);//等待字节写入完成,等待时间不足会影响下一个字节的写入while(s4 == 0){smg_dispaly();}}}if(s5 == 0){delay_key(TKEY);if(s5 == 0){num2++;if(num2 > 13){num2 = 0;}write_24c02(0x01, num2);delay_24c02(CKEY);while(s5 == 0){smg_dispaly();}}}if(s6 == 0){delay_key(TKEY);if(s6 == 0){num3++;if(num3 > 13){num3 = 0;}write_24c02(0x02, num3);delay_24c02(CKEY);while(s6 == 0){smg_dispaly();}}}
}//单字节写入
void write_24c02(unsigned char addr, unsigned char dat)
{I2CStart();I2CSendByte(0xa0);I2CWaitAck();I2CSendByte(addr);I2CWaitAck();I2CSendByte(dat);I2CWaitAck();I2CStop();}//单字节读取
unsigned char read_24c02(unsigned char addr)
{unsigned char temp = 0;I2CStart();I2CSendByte(0xa0);I2CWaitAck();I2CSendByte(addr);I2CWaitAck();I2CStart();I2CSendByte(0xa1);I2CWaitAck();temp = I2CReceiveByte();I2CSendAck(1);I2CStop();return temp;
}#include "intrins.h"#define DELAY_TIME	5//
static void I2C_Delay(unsigned char n)
{do{_nop_();_nop_();_nop_();_nop_();_nop_();_nop_();_nop_();_nop_();_nop_();_nop_();_nop_();_nop_();_nop_();_nop_();_nop_();		}while(n--);      	
}//
void I2CStart(void)
{sda = 1;scl = 1;I2C_Delay(DELAY_TIME);sda = 0;I2C_Delay(DELAY_TIME);scl = 0;    
}//
void I2CStop(void)
{sda = 0;scl = 1;I2C_Delay(DELAY_TIME);sda = 1;I2C_Delay(DELAY_TIME);
}//
void I2CSendByte(unsigned char byt)
{unsigned char i;for(i=0; i<8; i++){scl = 0;I2C_Delay(DELAY_TIME);if(byt & 0x80){sda = 1;}else{sda = 0;}I2C_Delay(DELAY_TIME);scl = 1;byt <<= 1;I2C_Delay(DELAY_TIME);}scl = 0;  
}//
unsigned char I2CReceiveByte(void)
{unsigned char da;unsigned char i;for(i=0;i<8;i++){   scl = 1;I2C_Delay(DELAY_TIME);da <<= 1;if(sda) da |= 0x01;scl = 0;I2C_Delay(DELAY_TIME);}return da;    
}//
unsigned char I2CWaitAck(void)
{unsigned char ackbit;scl = 1;I2C_Delay(DELAY_TIME);ackbit = sda; scl = 0;I2C_Delay(DELAY_TIME);return ackbit;
}//
void I2CSendAck(unsigned char ackbit)
{scl = 0;sda = ackbit; I2C_Delay(DELAY_TIME);scl = 1;I2C_Delay(DELAY_TIME);scl = 0; sda = 1;I2C_Delay(DELAY_TIME);
}void init_sys()
{hc573(5,0x00);   //关闭蜂鸣器和继电器hc573(4,0xff);   //熄灭LEDsmg_all(0xff);   //关闭所有数码管//读出历史计数num1 = read_24c02(0x00);num2 = read_24c02(0x01);num3 = read_24c02(0x02);
}void main()
{init_sys();while(1){smg_dispaly();key();}
}
  1. hc573函数用于控制特定通道的输出,根据传入的通道号和数据值设置输出信号。
  2. delay_smgdelay_keydelay_24c02函数实现了不同延时功能。
  3. Seg_Table数组存储了数码管显示的段选值。
  4. smg_all函数和smg_bit函数用于控制数码管的显示。
  5. smg_display函数从24C02存储器的不同地址单元读取数据,并将数据显示在数码管上。
  6. key函数实现了按键操作,根据按键S4、S5和S6的按下次数进行累加,并将最新次数写入24C02存储器的对应单元。
  7. write_24c02函数用于向24C02存储器写入数据。
  8. read_24c02函数用于从24C02存储器读取数据。
  9. I2CStartI2CStopI2CSendByteI2CReceiveByte等函数实现了I2C总线通信的基本操作。
  10. init_sys函数用于初始化系统,包括关闭蜂鸣器、继电器和LED灯,读取历史计数数据。
  11. main函数是程序的入口,首先进行系统初始化,然后进入一个无限循环,持续进行数码管的显示和按键操作。

如果需要进一步解释或有任何疑问,请联系或者看往期内容。

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

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

相关文章

基于springboot+vue的旅游网站

博主主页&#xff1a;猫头鹰源码 博主简介&#xff1a;Java领域优质创作者、CSDN博客专家、阿里云专家博主、公司架构师、全网粉丝5万、专注Java技术领域和毕业设计项目实战&#xff0c;欢迎高校老师\讲师\同行交流合作 ​主要内容&#xff1a;毕业设计(Javaweb项目|小程序|Pyt…

JavaScript 权威指南第七版(GPT 重译)(六)

第十五章&#xff1a;JavaScript 在 Web 浏览器中 JavaScript 语言是在 1994 年创建的&#xff0c;旨在使 Web 浏览器显示的文档具有动态行为。自那时以来&#xff0c;该语言已经发生了显著的演变&#xff0c;与此同时&#xff0c;Web 平台的范围和功能也迅速增长。今天&#…

2024.3.24阶段性测试题解

VJ测试链接考试链接 成绩表如下&#xff0c;信息学是非常检验平时努力的&#xff0c;而且也是一分耕耘一分收获的&#xff0c;总的来说每天订正晚训跟只订正一部分题还是有区别的…希望同学们再接再厉。 A题 简单判断题&#xff0c;单独判断首字母&#xff0c;再判断其余字母…

Java 学习和实践笔记(45):数组的遍历,复制,

数组的两种遍历方式&#xff1a; package innerClass;public class Test01 {public static void main(String[] args) {String[] cities {"北京","上海","广州","深圳",};//遍历方式一&#xff0c;这是一般的方式for (int i0; i<…

AI大模型学习:理论基石、优化之道与应用革新

✨✨ 欢迎大家来访Srlua的博文&#xff08;づ&#xffe3;3&#xffe3;&#xff09;づ╭❤&#xff5e;✨✨ &#x1f31f;&#x1f31f; 欢迎各位亲爱的读者&#xff0c;感谢你们抽出宝贵的时间来阅读我的文章。 我是Srlua小谢&#xff0c;在这里我会分享我的知识和经验。&am…

列车票务信息管理系统设计与实现|jsp+ Mysql+Java+ B/S结构(可运行源码+数据库+设计文档)

本项目包含可运行源码数据库LW调试部署环境&#xff0c;文末可获取本项目的所有资料。 推荐阅读100套最新项目 最新ssmjava项目文档视频演示可运行源码分享 最新jspjava项目文档视频演示可运行源码分享 最新Spring Boot项目文档视频演示可运行源码分享 2024年56套包含java…

100道面试必会算法-11-LFU缓存

100道面试必会算法-11-LFU缓存 题目描述 最不经常使用&#xff08;LFU&#xff09;缓存算法设计并实现数据结构。 实现 LFUCache 类&#xff1a; LFUCache(int capacity) - 用数据结构的容量 capacity 初始化对象int get(int key) - 如果键 key 存在于缓存中&#xff0c;则…

mysql 事务的四大特性以及实现原理

MySQL 事务的四大特性通常指ACID&#xff0c;即原子性&#xff08;Atomicity&#xff09;、一致性&#xff08;Consistency&#xff09;、隔离性&#xff08;Isolation&#xff09;和持久性&#xff08;Durability&#xff09;。 原子性&#xff08;Atomicity&#xff09;&…

OpenLayers基础教程——WebGLPoints中要素样式的设置方法解析

1、前言 前一篇博客介绍了如何在OpenLayers中使用WebGLPoints加载海量数据点的方法&#xff0c;这篇博客就来介绍一下WebGLPoints图层的样式设置问题。 2、样式运算符 在VectorLayer图层中&#xff0c;我们只需要创建一个ol.style.Style对象即可&#xff0c;WebGLPoints则不…

重新排序(蓝桥杯,acwing,差分)

题目描述&#xff1a; 给定一个数组 A 和一些查询 Li,Ri&#xff0c;求数组中第 Li至第 Ri 个元素之和。 小蓝觉得这个问题很无聊&#xff0c;于是他想重新排列一下数组&#xff0c;使得最终每个查询结果的和尽可能地大。 小蓝想知道相比原数组&#xff0c;所有查询结果的总…

Photoshop 工具使用详解(全集 · 2024版)

全面介绍 Photoshop 工具箱里的工具&#xff0c;点击下列表格中工具名称或图示&#xff0c;即可查阅工具的使用详解。 移动工具Move Tool移动选区、图层和参考线。画板工具Artboard Tool创建、移动多个画布或调整其大小。moVe快捷键&#xff1a;V 矩形选框工具 Rectangular Mar…

信号处理之快速傅里叶变换(FFT)

信号处理之快速傅里叶变换FFT 历史溯源欧拉公式傅里叶级数(FS)傅里叶变换(FT)离散傅里叶级数(DFS)离散时间傅里叶变换(DTFT)离散傅里叶变换(DFT)快速傅里叶变换(FFT)MATLAB中常用的FFT工具FFT中常见的问题 历史溯源 相信很多人知道傅里叶变换&#xff0c;但是很多人对傅里叶变…

EtherCAT主站SOEM -- 20 --Qt-Soem通过 PT模式(力矩模式)控制一个电机转圈圈

EtherCAT主站SOEM -- 20 --Qt-Soem通过 PT模式(力矩模式)控制一个电机转圈圈 0 QT-SOEM视频预览及源代码下载:0.1 QT-SOEM视频预览0.2 QT-SOEM源代码下载PS 特别注意1 程序文件修改替换1.1 allvalue.h1.2 motrorcontrol.h1.3 mainwindow.cpp1.4 motrorcontrol.cpp2 ui界面显…

【Springboot3+Mybatis】文件上传阿里云OSS 基础管理系统CRUD

文章目录 一、需求&开发流程二、环境搭建&数据库准备三、部门管理四、员工管理4.1 分页(条件)查询4.2 批量删除员工 五、文件上传5.1 介绍5.2 本地存储5.3 阿里云OSS1. 开通OSS2. 创建存储空间Bucket 5.4 OSS快速入门5.5 OSS上传显示文件 六、配置文件6.1 yml配置6.2 C…

云原生(五)、Docker-Swarm集群

基础环境说明 1、环境准备 1、启动4台服务器&#xff08;在同一个网段内&#xff09;。 2、重命名4台服务器&#xff0c;方便区分。 hostnamectl set-hostname swarm1 reboot安装docker。参考文章&#xff1a;云原生&#xff08;二&#xff09;、Docker基础 2、DockerSwarm…

Qt打开已有工程方法

在Qt中&#xff0c;对于一个已有工程如何进行打开&#xff1f; 1、首先打开Qt Creator 2、点击文件->打开文件或项目&#xff0c;找到对应文件夹下的.pro文件并打开 3、点击配置工程 这样就打开对应的Qt项目了&#xff0c;点击运行即可看到对应的效果 Qt开发涉及界面修饰…

Python从入门到精通秘籍十八

一、Python之继承的基础语法 在Python中&#xff0c;继承是面向对象编程的一个重要概念&#xff0c;它允许一个类&#xff08;称为子类&#xff09;从另一个类&#xff08;称为父类或基类&#xff09;继承属性和方法。子类可以使用继承的属性和方法&#xff0c;并且还可以添加…

jmeter断言使用方法

断言主流的有两种&#xff1a;响应断言、JSON断言 响应断言 1、http请求添加响应断言 2、三种作用域&#xff1a;第一种既作用主请求又作用子请求、只作用主请求、只作用子请求。我们默认选中间的仅作用主请求即可。 3、测试字段和匹配规则 测试字段一般选择响应文本即可&am…

机器学习的步骤与方法

一、引言&#xff1a; 机器学习是人工智能的分支之一&#xff0c;旨在研究如何使计算机系统自主地从数据中学习&#xff0c;并能够根据以往的经验做出预测或决策。现代机器学习主要使用统计学、概率论和优化算法来构建模型和训练算法。 应用场景&#xff1a; 机器学习在众多领…

web渗透测试漏洞流程:google hacking语法具体语句示例

web渗透测试漏洞流程 渗透测试信息收集---域名信息收集2.1.1.3 GoogleHacking用法示例管理后台地址上传类漏洞地址注入页面编辑器页面目录遍历漏洞SQL错误phpinfo()配置文件泄露数据库文件泄露日志文件泄露备份和历史文件泄露公开文件泄露邮箱信息社工信息搜索文件