绿70秒,黄3秒,红60秒
使用软件Proteus和Keil uVision4
代码如下:
#include<reg51.h>
char code table[]={0xc0,0xf9,0xa4,0xb0,0x99,0x92,0x82,0xf8,0x80
,0x90,0x88,0x83,0xc6,0xa1,0x86,0x8e};//把数组放入ROM中
sbit green=P1^0;
sbit yellow=P1^1;
sbit red=P1^2;
//设计绿灯70s,黄灯3s,红灯60s,所以时间周期是133s
char tmp=0,sec=133;//红黄绿灯都是倒计时
main()
{
//定时器的初始化
TMOD=0x01;//定时器方式一的设置
TR0=1;//time run
ET0=1;//定时器的使能
EA=1; //总中断打开
TH0=(65536-50000)/256;//50ms定时一次,高8位
TL0=(65536-50000)%256;//50ms定时一次,低8位
P3=0;//一开始,把所有的P3口都置0,相当于把所有的三极管都关闭
while(1)
{
if(sec==0)//说明一个周期已经运行完了,进入下一个周期
{
sec=133;
}
if(sec>63)//绿灯时间点,数码管显示的数字70-1,133>=sec>=64
{
green=0;//绿灯亮
yellow=1;//黄灯灭
red=1;//红灯灭
P2=table[(sec-63)/10];
P3=table[(sec-63)% 10];
}
else if(sec>60)//此时sec满足63>=sec>=61
{
green=1;//绿灯灭
yellow=0;//黄灯亮
red=1;//红灯灭
P2=table[(sec-60)/10];//显示的数字3到1
P3=table[(sec-60)% 10];//显示的数字3到1
}
else
{
green=1;//绿灯灭
yellow=1;//黄灯灭
red=0;//红灯亮
P2=table[sec/10];//显示的数字60到1
P3=table[sec%10];//显示的数字60到1
}
}
}
void time0()interrupt 1//interrupt是中断标志号1一定要与中断类型对应上,50ms进入一次中断函数
//CPU接收到了中断的请求后,会自动执行这个函数,不要在main函数中调用
//定时器与延时相比,延时是需要调用,定时就像后台自动执行
//定时器的CPU工作效率比较高
{
TH0=(65536-50000)/256;//50ms定时一次,高8位
TL0=(65536-50000)%256;//50ms定时一次,低8位
//如果不重置TH0和TL0,那下一轮的中断就变成了65.536ms
tmp++;//每隔50ms加一,加到多少就变成1s,20次
if(tmp==20)//这逻辑成立,代表是1s到
{
tmp=0;//计算下一轮的1s,让tmp置0
sec--;//每隔一秒要减一
}
}//时间处理
电路仿真效果
问题:绿灯的时候,数字显示不完整。有大佬能帮我看看怎么解决。