米拓cms建站系统,哪家公司设计网站好,故乡网站开发的意义,网上帮人卖东西的平台前言
本篇文章属于STC89C52单片机#xff08;以下简称单片机#xff09;的学习笔记#xff0c;来源于B站教学视频。下面是这位up主的视频链接。本文为个人学习笔记#xff0c;只能做参考#xff0c;细节方面建议观看视频#xff0c;肯定受益匪浅。
[1-1] 课程简介_哔哩…前言
本篇文章属于STC89C52单片机以下简称单片机的学习笔记来源于B站教学视频。下面是这位up主的视频链接。本文为个人学习笔记只能做参考细节方面建议观看视频肯定受益匪浅。
[1-1] 课程简介_哔哩哔哩_bilibili
一、存储器介绍
存储器介绍 易失性存储器/RAMrandom access memory 随机存储器掉电会丢失
SRAM静态RAM速度较快
DRAM速度不如静态RAM
非易失性存储器/ROMread only memory 只读存储器掉电不会丢失
Mask ROM掩膜ROM不能写入只能读取
PROM可编程ROM只能写入一次
EPROM可擦除可编程ROM紫外线照射30分钟才能擦除数据
EEPROM电可擦除可编程ROM可以通过电来迅速擦除 存储器的简化模型 烧录一词的由来通过烧穿二极管来实现导通
二、AT24C02介绍 引脚及应用电路 内部结构框图 三、I2C总线
1.I2C总线介绍 2.I2C电路规范 单片机的弱上拉模式
要输出低电平0时闭合开关无电阻经过驱动能力较强
要输出高电平1时断开开关有电阻经过驱动能力较弱 开漏输出 把上拉电阻去掉
输出低电平时闭合开关即可
输出高电平时断开开关IO口处于一个浮空的状态 3.I2C时序结构
起始位与终止位 发送一个字节 接受一个字节 从机应答 I2C数据帧
发送 接受 复合格式 AT24C02数据帧 四、实例一AT24C02数据存储 I2C.c #include REGX52.Hsbit I2C_SCLP2^1;
sbit I2C_SDAP2^0;/*** brief I2C开始 * param 无* retval 无*/
void I2C_Start(void)
{I2C_SDA1;I2C_SCL1;I2C_SDA0;I2C_SCL0;
}/*** brief I2C停止* param 无* retval 无*/
void I2C_Stop(void)
{I2C_SDA0;I2C_SCL1;I2C_SDA1;
}/*** brief I2C发送一个字节* param Byte 要发送的字节* retval 无*/
void I2C_SendByte(unsigned char Byte)
{unsigned char i;for (i0;i8;i){I2C_SDAByte(0x80i);I2C_SCL1;I2C_SCL0;}
}/*** brief I2C接受一个字节* param 无* retval 接受到的一个字节数据*/
unsigned char I2C_ReceiveByte(void)
{unsigned char i,Byte0x00;I2C_SDA1;for (i0;i8;i){I2C_SCL1;if(I2C_SDA){Byte|(0x80i);}I2C_SCL0;}return Byte;
}/*** brief I2C发送应答* param AckBit 应答位0为应答1为非应答* retval 无*/
void I2C_SendAck(unsigned char AckBit)
{I2C_SDAAckBit;I2C_SCL1;I2C_SCL0;
}/*** brief I2C接受应答* param 无* retval 接受到的应答位*/
unsigned char I2C_ReceiveAck(void)
{unsigned char Ackbit;I2C_SDA1;I2C_SCL1;AckbitI2C_SDA;I2C_SCL0;return Ackbit;
} AT24C02.c --继承I2C的字节帧形成数据帧 #include REGX52.H
#include I2C.h// SLAVE ADDRESSW为0xA0SLAVE ADDRESSR为0xA1
#define AT24C02_ADDRESS_READ 0xA0
#define AT24C02_ADDRESS_WRITE 0xA1/*** brief AT24C02写入一个字节* param WordAddress 要写入字节的地址* param Data 要写入的数据* retval 无*/
void AT24C02_WriteByte(unsigned char WordAddress,Data)
{I2C_Start();I2C_SendByte(AT24C02_ADDRESS_READ);I2C_ReceiveAck();I2C_SendByte(WordAddress);I2C_ReceiveAck();I2C_SendByte(Data);I2C_ReceiveAck();I2C_Stop();
}/*** brief AT24C02读取一个字节* param WordAddress 要读出字节的地址* retval 读出的数据*/
unsigned char AT24C02_ReadByte(unsigned char WordAddress)
{unsigned char Data;I2C_Start();I2C_SendByte(AT24C02_ADDRESS_READ);I2C_ReceiveAck();I2C_SendByte(WordAddress);I2C_ReceiveAck();I2C_Start();// 读地址I2C_SendByte(AT24C02_ADDRESS_WRITE);I2C_ReceiveAck();DataI2C_ReceiveByte();I2C_SendAck(1);I2C_Stop();return Data;
} 注意调用AT24C02_WriteByte时要延时5ms让数据有充分的时间写入 五、实例二秒表定时器扫描按键数码管 在定时器的中断函数中调用按键扫描和数码管扫描的函数实现定时器的复用 Key.c #include REGX52.H
#include Delay.hunsigned char Key_KeyNum;unsigned char Key()
{unsigned char Temp0;TempKey_KeyNum;Key_KeyNum0;return Temp;
}unsigned char Key_GetState()
{unsigned char KeyNumber0;if(P3_10){KeyNumber1;}if(P3_00){KeyNumber2;}if(P3_20){KeyNumber3;}if(P3_30){KeyNumber4;}return KeyNumber;
}void Key_Loop(void)
{static unsigned char NowState,LastState;LastStateNowState;NowStateKey_GetState();//Last1,Now0检测的是松手Last0Now1检测的是按下if (LastState1 NowState0){Key_KeyNum1;}if (LastState2 NowState0){Key_KeyNum2;}if (LastState3 NowState0){Key_KeyNum3;}if (LastState4 NowState0){Key_KeyNum4;}
} Nixie.c #include REGX52.H
#include Delay.hunsigned char Nixie_Buf[9]{0,10,10,10,10,10,10,10,10};unsigned char NixieTable[]{0x3F,0x06,0x5B,0x4F,0x66,0x6D,0x7D,0x07,0x7F,0x6F,0x00,0x40};void Nixie_SetBuf(unsigned char Location,Number)
{Nixie_Buf[Location]Number;
}void Nixie_Scan(unsigned char Location,Number)
{P00x00;switch(Location){case 1:P2_41;P2_31;P2_21;break;case 2:P2_41;P2_31;P2_20;break;case 3:P2_41;P2_30;P2_21;break;case 4:P2_41;P2_30;P2_20;break;case 5:P2_40;P2_31;P2_21;break;case 6:P2_40;P2_31;P2_20;break;case 7:P2_40;P2_30;P2_21;break;case 8:P2_40;P2_30;P2_20;break;}P0NixieTable[Number];
}void Nixie_Loop(void)
{static unsigned char i1;Nixie_Scan(i,Nixie_Buf[i]);i;if(i8){i1;}
} main.c #include REGX52.H
#include Key.h
#include Nixie.h
#include Timer0.h
#include AT24C02.h
#include Delay.hunsigned char KeyNum;
unsigned char Temp;
unsigned char Min,Sec,MiniSec;
unsigned char RunFlag;void main()
{Timer0_Init();while(1){KeyNumKey();if(KeyNum1){RunFlag!RunFlag;}if(KeyNum2){Min0;Sec0;MiniSec0;}if(KeyNum3){AT24C02_WriteByte(0,Min);Delay(5);AT24C02_WriteByte(1,Sec);Delay(5);AT24C02_WriteByte(2,MiniSec);Delay(5);}if(KeyNum4){MinAT24C02_ReadByte(0);SecAT24C02_ReadByte(1);MiniSecAT24C02_ReadByte(2);}Nixie_SetBuf(1,Min/10);Nixie_SetBuf(2,Min%10);Nixie_SetBuf(3,11);Nixie_SetBuf(4,Sec/10);Nixie_SetBuf(5,Sec%10);Nixie_SetBuf(6,11);Nixie_SetBuf(7,MiniSec/10);Nixie_SetBuf(8,MiniSec%10);}
}void Sec_Loop()
{if (RunFlag){MiniSec;if (MiniSec100){MiniSec0;Sec;if (Sec60){Sec0;Min;if (Min100){Min0;}}}}
}void Timer0_Rountine() interrupt 1
{static unsigned int T0Count1,T0Count2,T0Count3;TH00xFC; TL00x66; T0Count1;if (T0Count120) {T0Count10;Key_Loop();}T0Count2;if (T0Count22) {T0Count20;Nixie_Loop();}T0Count3;if (T0Count310){T0Count30;Sec_Loop();}
}