9.15学习笔记

数码管的动态显示:精简代码版,要注意关灯,否则有问题,还有时间消影,这个例子虽然很简单,但是精简代码百分之九十的人会写错

#include<reg52.h>
#define uint unsigned int
#define uchar unsigned char

void delay(uint z);
uchar code table[]={ 0x3f,0x06,0x5b,0x4f,
					0x66,0x6d,0x7d,0x07,
					0x7f,0x6f,0x77,0x7c,
					0x39,0x5e,0x79,0x71};

uchar code tablew[]={0xfe,0xfd,0xfb,0xf7,
					0xef,0xdf,0xbf,0x7f};

uchar aa,bb;
uint tt;
sbit dula =P2^6;
sbit wela = P2^7;

main()
{
	aa = 0;
	bb = 6;
	
	while(1)
	{
		wela = 1;
		P0 = tablew[aa];
		wela = 0;
		P0 = 0xff;
		//delay(1);

	
		dula = 1;
		P0 = table[bb];
		dula = 0;
		P0 = 0xff;
		tt=300;
		while(tt--);

		dula = 1;
		P0 = 0x0;//要关灯,或者这个程序有问题,
		dula = 0;

		delay(1);

		
		aa ++;
		bb--;
	
	
		if(aa == 6)
			aa = 0;
		if(bb ==0)
			bb = 6;
		
	}
	while(1);
}

void delay(uint z)
{
	uint x,y;
	for(x = z;x>0;x--)
		for(y=110;y>0;y--);

}

 作业2:用数码管的动态扫描制成一个秒表,让数码管后两位显示%1秒

//程序虽然写出来了,但是调试可是花了我大力气, 对于数码管而言   
//要记住,不要使用delay()郭天祥那个延时函数,因为这里涉及的是微妙级别的数    
//display这个函数执行的时间不能大于10微秒,这就必须消影,
//高速度扫描时,不消影后果很严重,每次段选完以后要进行关灯   
//timu:有两个动态扫描的方法和定时器1在数码管的前三位显示表秒
//精确到%1,即后两位显示百分之一秒,一直循环下去 
//关于定时器装初值问题,这里有一个规律,就是,12Mhz的晶振,计数恋
//计数N毫秒,就装入N乘以1000 
#include<reg52.h>
#define uint unsigned int
#define uchar unsigned char

uint num;
uchar aa,bb,ge,shi,bai,tt;
sbit  wela =P2^6;
sbit dula = P2^7;
void init();
void delay(uint z);
void display(uchar bai,uchar shi,uchar ge);
uchar code table[]={0x3f,0x06,0x5b,0x4f,
					0x66,0x6d,0x7d,0x07,
					0x7f,0x6f,0x77,0x7c,
					0x39,0x5e,0x79,0x71};

main()
{
	init();
	while(1)
	{
		if(aa==10)
		{	aa = 0;
			num++;
			if(num == 1000)
			num=0;
		}
		ge = num%10;
		shi = num/10%10;
		bai = num/100;
		
		display(ge,shi,bai);
	}

}

void init()
{
	TMOD = 0x11;
	TH1 = (65535-1000)/256;
	TL1 = (65535-1000)%256;

	EA = 1;//开总中断
	ET1 = 1;//开定时器1中断
	TR1 = 1;//启动定时器1
	aa = 0;

}

void display(uchar bai,uchar shi,uchar ge)
{
	wela = 1;
	P0 = 0xfe;
	wela = 0;
	P0 = 0x0;//消影操作

	dula = 1;
	P0 = table[ge];
	dula = 0;
	tt = 25;
	while(tt--);
	dula = 1;//关灯操作,高速度扫描时必备 
	P0 = 0;
	dula = 0;

	wela = 1 ;
	P0 = 0xfd;
	wela = 0;
	P0= 0x0;//消影操作

	dula = 1;
	P0 = table[shi];
	dula = 0;
	tt = 25;
	while(tt--);
	dula = 1;//关灯操作,高速度扫描时必备 
	P0 = 0;
	dula = 0;


	wela = 1;
	P0 = 0xfb;
	wela = 0;
	P0 = 0x0;//消影操作

	dula = 1;
	P0 = table[bai];
	dula =0;
	tt=25;
	while(tt --);
	
	dula = 1;//关灯操作,高速度扫描时必备 
	P0 = 0;
	dula = 0;

}
 

void time1()interrupt 3
{
	TH1 = (65535-1000)/256;
	TL1 = (65535-1000)%256;
	aa ++;

}

 作业3:利用动态扫描,和定时器1,在数码管上显示从765432开始以十分之一秒的速度往下递减直至765398,并且保持住此数,与此同时利用定时器0以500ms的速度进行流水灯从上往下移动,但数码管减到停止时,实验板上流水灯也停止,然后开始闪烁,3秒后,(用T0)计时,数码管上显示HELLO,并且保持住

//这个程序也调试了我好久,这里主要是标志位的使用  
//当一个事件接二连三的发生时,这里要考虑设置标志位
//定时器的关闭后,再次启动,需要重新装入初值,还要重新启动   

#include<reg52.h>
#include<intrins.h>

#define uint unsigned int
#define uchar unsigned char

sbit dula = P2^2;
sbit wela = P2^3;

uchar aa,bb,cc,dd,ee,ff,bai,shi,ge,flag,flag1;
uint num,tt;

void init();//一个机器周期执行时间就是1um  
void display(uchar cc,uchar dd,uchar ee,uchar bai,uchar shi,uchar ge);

uchar code table[]={0x3f,0x06,0x5b,0x4f,
					0x66,0x6d,0x7d,0x07,
					0x7f,0x6f,0x77,0x7c,
					0x39,0x5e,0x79,0x71,
					0x76,0x79,0x38,0x3f,0};

void main()
{
	init();
	bai = num/100;
	shi = num/10%10;
	ge = num%10;
	while(1)
	{
		if(flag1 != 1)
		{
			display(7,6,5,bai,shi,ge);
		}
		else
		{
			display(16,17,18,18,19,20);
		}
	}
	

}

void init()
{
	TMOD = 0x11;
	TH1 = (65535-50000)/256;
	TL1 = (65535-50000)%256;
	
	TH0 = (65535-50000)/256;
	TL0 = (65535-50000)%256;


	EA = 1;
	ET1 = 1;
	TR1 = 1;
	
	
	ET0 = 1;
	TR0 = 1;
	bb = 0;
	aa = 0xfe;
	ff = 0;
	num=432;
	flag = 0;
	flag1 = 0;

	
}

void display(uchar cc,uchar dd,uchar ee,uchar bai,uchar shi,uchar ge)
{
	wela = 1;
	P0 = 0xfe;
	wela = 0;
	P0 = 0x0;

	dula = 1;
	P0 = table[cc];
	dula = 0;
	P0 = 0xff;
	tt=50;
	while(tt--);
	dula = 1;
	P0=0;
	dula =0;

	wela = 1;
	P0 = 0xfd;
	wela = 0;
	P0 = 0x0;

	dula = 1;
	P0 = table[dd];
	dula = 0;
	P0 = 0xff;
	tt=50;
	while(tt--);
	dula = 1;
	P0=0;
	dula =0;

	wela = 1;
	P0 = 0xfb;
	wela = 0;
	P0 = 0x0;

	dula = 1;
	P0 = table[ee];
	dula = 0;
	P0 = 0xff;
	tt=50;
	while(tt--);
	dula = 1;
	P0=0;
	dula =0;

	wela = 1;
	P0 = 0xf7;
	wela = 0;
	P0 = 0x0;

	dula = 1;
	P0 = table[bai];
	dula = 0;
	P0 = 0xff;
	tt=50;
	while(tt--);
	dula = 1;
	P0=0;
	dula =0;

	wela = 1;
	P0 = 0xef;
	wela = 0;
	P0 = 0x0;

	dula = 1;
	P0 = table[shi];
	dula = 0;
	P0 = 0xff;
	tt=50;
	while(tt--);
	dula = 1;
	P0=0;
	dula =0;

	wela = 1;
	P0 = 0xdf;
	wela = 0;
	P0 = 0x0;

	dula = 1;
	P0 = table[ge];
	dula = 0;
	P0 = 0xff;
	tt=50;
	while(tt--);
	dula = 1;
	P0=0;
	dula =0;

}

void time_0()interrupt 1
{

	TH0 = (65535-50000)/256;
	TL0 = (65535-50000)%256;
	bb++;
	if(flag!=1)
	{
		if(bb==10)
		{
			bb = 0;
			aa = _crol_(aa,1);
			P1 = aa;
		}
		
	}
	else
	{
		if(bb%2==0)
		{
			
			P1 = ~P1;
			if(bb==30)
			{
				TR0 = 0;
				P1 = 0xff;
				flag1 = 1;
			}
		}
	
	}


}

void time1()interrupt 3
{
	TH1 = (65535-50000)/256;
	TL1 = (65535-50000)%256;
	ff++;
	if(ff==2)
	{	
		ff = 0;
		num --;
		if(num == 357)
			{
			TR0 = 0;
			TR1 = 0;
			flag = 1;
			
			TH0 = (65536-50000)/256;//重新装入初值
			TL0 = (65536-50000)%256;
			TR0 = 1;
			
			}
		bai = num/100;
		shi = num/10%10;
		ge = num%10;
	}
}

关于中断函数中写入多少程序好的分析:中断函数假设为50毫秒,程序执行的时间不要超过50毫秒,一个机器周期大约是1微妙,单周期指令,双周期指令,那么撑死他有1000,行,才是1毫秒,一般的不要太复杂,所以,在中断函数中,做一些有利于观察,有利于计算的就行了

 

 

版权所有,转载请注明链接地址:http://www.cnblogs.com/fengdashen/p/3322170.html

 

posted @ 2013-09-17 20:56  跨七海的风  阅读(391)  评论(0编辑  收藏  举报