系统实验报告学院XXXXXXXXX专业XXXXXX姓名XXXXX学号XXXXXXX一、本设计拟实现的功能1.时钟:四只数码管低二位0~59计数后给高二位0~59计数(即分秒计时),一只按键控制开始、结束;2.交通灯:灯和数码管结合,模拟十字路口的交通灯的点亮与熄灭,数码管倒计时显示时间。
二、所用器件的功能、引脚图1.所用器件:AT89S51、74LS47、LM70852.所用器件功能、引脚图a)AT89S51AT89S51引脚图AT89S51是一个低功耗,高性能CMOS 8位单片机,片内含4k Bytes ISP(In-system programmable)的可反复擦写1000次的Flash只读程序存储器,器件采用ATMEL公司的高密度、非易失性存储技术制造,兼容标准MCS-51指令系统及80C51引脚结构,芯片内集成了通用8位中央处理器和ISP Flash存储单元,AT89S51在众多嵌入式控制应用系统中得到广泛应用。
主要性能特点1、4k Bytes Flash片内程序存储器;2、128 bytes的随机存取数据存储器(RAM);3、32个外部双向输入/输出(I/O)口;4、5个中断优先级、2层中断嵌套中断;5、6个中断源;6、2个16位可编程定时器/计数器;7、2个全双工串行通信口;8、看门狗(WDT)电路;9、片内振荡器和时钟电路;10、与MCS-51兼容;11、全静态工作:0Hz-33MHz;12、三级程序存储器保密锁定;13、可编程串行通道;14、低功耗的闲置和掉电模式。
b) 74LS4774LS47引脚图74LS47真值表74LS47是一种常用的BCD--七段数码管译码器驱动器,74LS47的输入端是四位二进制信号(8421BCD码),a、b、c、d、e、f、g是七段译码器的输出驱动信号,低电平有效。
可直接驱动共阴极七段数码管,是使能端,起辅助控制作用。
使能端的作用如下:(1) LT是试灯输入端,当 LT=0, BI=1时,不管其它输入是什么状态,a~g七段全亮;(2)BI静态灭灯输入,当 BI=0,不论其它输入状态如何,a~g 均为0,显示管熄灭;(3)RBI动态灭零输入,当 LT=1, RBI=0时,如果 A3A2A1A0(ABCD)=0000时,a~g均为各段熄灭;(4) RBO动态灭零输出,它与灭灯输入BI 共用一个引出端。
当在动态灭零时输出才为0。
片间与 RBI配合,可用于熄灭多位数字前后所不需要显示的零。
c) LM7805LM7085引脚图7805是常用到的稳压芯片,外围电路简单,输出电压为5V,可为51单片机提供工作电压。
三、软件设计流程图四、源程序#include <reg51.h>#define uchar unsigned char#define uint unsigned int#define TH_SET 0x4C#define TL_SET 0x00 //定时50ms的初始值#define RTime 24 // 红灯时间20s#define GTime 24 // 绿灯时间20s#define YTime 3 //黄灯时间5ssbit KEY_A=P1^0;sbit KEY_B=P1^1;sbit GREEN1=P2^0;sbit GREEN2=P2^3;sbit RED1=P2^1;sbit RED2=P2^4;sbit YELLOW1=P2^2;sbit YELLOW2=P2^5;//位定义bit key1=0,key2=0;//四个按键状态标志uint time1,time2;//time1,time2分别为键1、键2功能实现的时间变量uchar acount,keyflag,Status=1,yellow=0;//acount定时一秒标志//Status交通灯状态显示标志,keyflag按键选择标志,P黄灯闪烁定时标志void Delay(int n){ //延时程序uint i;uint j;for(i=0;i<n;i++){for(j=0;j<200;j++);}}//定时器0void Timer0_SVR() interrupt 1{TH0=TH_SET;TL0=TL_SET;acount++;if(KEY_A==0){//按键扫描实现暂停和按键切换Delay(2);if(KEY_A==0){key1=~key1 ;keyflag=1;while(!KEY_A);}}if(KEY_B==0){Delay(2);if(KEY_B==0){key2=~key2 ;keyflag=2;while(!KEY_B);}}if(acount==20){//IntCount=20定时一秒acount=0; //定时一秒恢复if(keyflag==1){if(key1==1){//按下键1使交通灯显示时间自减time1--;if(time1==0){Status++;//显示时间为零时,切换交通灯状态 if(Status==5){Status=1;}}}}if(keyflag==2){if(key2==1){time2++; //按下键2时计时器时间自增if(time2==3600){//计时满一小时时归零time2=0;}}}}EA=1;}//计时器数码管显示函数void xianshi1(void){P0=time2/600+0x10;Delay(2); //分的十位P0=(time2/60%10)+0x20;Delay(2); //分的个位P0=((time2%60)/10)+0x40;Delay(2); //秒的十位P0=(time2%60%10)+0x80;Delay(2); //秒的个位}//交通灯数码管显示函数void xianshi2(void){P0=(time1/10)+0x50;Delay(2); //秒的十位P0=(time1%10)+0xA0;Delay(2); //秒的个位 yellow++;}//计数器状态函数void Count(){time2=0;key2=1;P2=0x80;while(1){if(keyflag==2){xianshi1();}elsebreak;}}//交通灯状态函数void TraLight(void){key1=1;time1=0;P2=0x80;while(1){if(Status==1&&time1==0){//Status=1时南北向红绿灯亮RED1=0;RED2=1;YELLOW1=0;YELLOW2=0;GREEN1=1;GREEN2=0;time1=GTime;}if(Status==2&&time1==0){//Status=2时黄灯闪烁RED1=0;RED2=0;YELLOW1=1;YELLOW2=1;GREEN1=0;GREEN2=0;time1=YTime;}if(Status==3&&time1==0){//Status=3时东西向红绿灯亮RED1=1;RED2=0;YELLOW1=0;YELLOW2=0;GREEN1=0;GREEN2=1;time1=RTime;}if(Status==4&&time1==0){//Status=4时黄灯闪烁RED1=0;RED2=0;YELLOW1=1;YELLOW2=1;GREEN1=0;GREEN2=0;time1=YTime;}if(yellow==50&&key1){//Status=2或4时为黄灯,实现闪烁if(Status==2||Status==4){yellow=0;YELLOW1=~YELLOW1; YELLOW2=~YELLOW2; }}if(keyflag==1){xianshi2();}elsebreak;}}void choose(void){switch(keyflag){case 1:TraLight();break;// 按键1case 2:Count();break; // 按键2default: break;}}//主函数void main(){//初始化定时器0EA=1;ET0=1;TMOD=0x01;TH0=0x4c;TL0=0x00;P2=0x80;if(KEY_A==0){ //按键扫描实现暂停和切换Delay(5);if(KEY_A==0){key1=~key1 ;keyflag=1;while(!KEY_A);}}if(KEY_B==0){Delay(5);if(KEY_B==0){key2=~key2 ;keyflag=2;while(!KEY_B);}}TR0=1;while(1){choose();}}六、已实现的功能1.KEYA:交通灯灯和数码管结合,模拟十字路口的交通灯的点亮与熄灭,数码管倒计时显示时间。
亮灯方式:红(20s)黄(闪烁5s)绿(20s)黄(闪烁5s)红(20s)数码管显示方式:南北向红绿灯20s 黄灯闪烁5s东西向红绿灯20s 黄灯闪烁5s南北向红绿灯20s按下KEYA可实现计时与红绿灯暂停2.KEYB:计时器四只数码管低二位0~59计数后给高二位0~59计数(即分秒计时)按下KEYB可实现计时器暂停七、调试过程步骤1:运行Keil uVision3新建工程并将程序代码输入,编译无错误后生成HEX文件。
步骤2:将HEX文件通过专业烧录软件烧录到AT89S51芯片中。
步骤3:上电按键操作,看是否符合设计要求。
步骤4:根据上电操作结果修改程序,并再次烧录调试,直至满足设计要求为止。
八、心得小结在焊接电路板的时候需要认真仔细,焊接时要先焊接体积较小的元器件,再焊接较大的元器件,这样比较方便,同时要看清三极管,排阻,二极管等带有方向性元器件,不要搞错方向,对于焊锡的把握适量即可,太多或太少都会导致虚焊。
在编写程序的过程中,最重要的是想好框架,然后从小处入手,先完成每个按键的功能,均能实现后,再将各个功能统筹在一起,这样程序不但简单易读还不容易出错。
当然在写程序的过程中也遇到了一些问题,比如在实现计时器功能时,每次计时到4分15秒时就归零了,后来发现原来是计时器中的计时变量time2用的是char型,而char型的计数范围为0——255,后来将char改为int型后,这个问题就得到了解决。
总之对于程序的调试最重要的还是反复的去尝试和分析问题的可能性,一步步的解决它,这样总是能完成任务的。