标题:
基于STC89C51单片机的加减乘除计算器仿真源程序
[打印本页]
作者:
了解@
时间:
2020-12-8 23:07
标题:
基于STC89C51单片机的加减乘除计算器仿真源程序
本帖最后由 了解@ 于 2020-12-9 00:28 编辑
计算器五位数以内+,-,*,/ 能识别优先级运算符
删除一个数或一个运算符
lcd1602显示
矩阵按键
程序proteus仿真原理图:
1602.PNG
(85.54 KB, 下载次数: 81)
下载附件
2020-12-8 22:50 上传
仿真代码:
#include<reg52.h>
#define uchar unsigned char
#define uint unsigned int
sbit rs=P2^0;//指令0,数据1
sbit rw=P2^1;//读0,写1,引脚
sbit lcden=P2^2;//使能端
uchar temp,num,flag,i,j,k,n,m,aa[10]={0},bb[11]={0};
uint sum[20]={0},count;
/**********************************************
延时函数 ms
*********************************************/
void delayms(uint t)
{
uint x,y;
for(x=t;x>0;x--)
for(y=110;y>0;y--);
}
/**********************************************
1602指令,数据,初始化
*********************************************/
void write_1602com(uchar com)
{
P0=com;
rs=0;//指令
rw=0;//写
lcden=0;
delayms(20);
lcden=1;
delayms(20);
lcden=0;
}
void write_1602date(uchar date)
{
P0=date;
rs=1;//数据
rw=0;//写
lcden=0;
delayms(20);
lcden=1;
delayms(20);
lcden=0;
}
void init_lcd1602()
{
write_1602com(0x38);//选择16x2显示,5x7点阵
delayms(20);
write_1602com(0x0f);//开显示,开光标,光标闪烁
delayms(20);
write_1602com(0x06);//读或写后,指针加一,光标加一
delayms(20);
write_1602com(0x01);//清屏
delayms(20);
}
/*****************************************
检测按键并输出
******************************************/
uchar keyscan()
{
P3=0xfe;
temp=P3;
while(temp!=0xfe)
{
delayms(5);
temp=P3;
while(temp!=0xfe)
{
switch(temp)
{
case 0xee:num=7;
break;
case 0xde:num=8;
break;
case 0xbe:num=9;
break;
case 0x7e:num='/';
break;
}
while(temp!=0xfe)
{
flag=1;
temp=P3;
}
}
}
P3=0xfd;
temp=P3;
while(temp!=0xfd)
{
delayms(5);
temp=P3;
while(temp!=0xfd)
{
switch(temp)
{
case 0xed:num=4;
break;
case 0xdd:num=5;
break;
case 0xbd:num=6;
break;
case 0x7d:num='*';
break;
}
while(temp!=0xfd)
{
flag=1;
temp=P3;
}
}
}
P3=0xfb;
temp=P3;
while(temp!=0xfb)
{
delayms(5);
temp=P3;
while(temp!=0xfb)
{
switch(temp)
{
case 0xeb:num=1;
break;
case 0xdb:num=2;
break;
case 0xbb:num=3;
break;
case 0x7b:num='-';
break;
}
while(temp!=0xfb)
{
flag=1;
temp=P3;
}
}
}
P3=0xf7;
temp=P3;
while(temp!=0xf7)
{
delayms(5);
temp=P3;
while(temp!=0xf7)
{
switch(temp)
{
case 0xe7:num='c';
break;
case 0xd7:num=0;
break;
case 0xb7:num='=';
break;
case 0x77:num='+';
break;
}
while(temp!=0xf7)
{
flag=1;
temp=P3;
}
}
}
return num;
}
/*********************************************
将逐个输入数 aa[] 转化为整数
*********************************************/
void zuan_shu()
{
switch(n)
{
case 0:sum[j++]=0;break;
case 1:sum[j++]=aa[0];break;
case 2:sum[j++]=aa[0]*10+aa[1];break;
case 3:sum[j++]=aa[0]*100+aa[1]*10+aa[2];break;
case 4:sum[j++]=aa[0]*1000+aa[1]*100+aa[2]*10+aa[3];break;
/* case 5:sum[j++]=aa[0]*10000+aa[1]*1000+aa[2]*100+aa[3]*10+aa[4];break;
case 6:sum[j++]=aa[0]*100000+aa[1]*10000+aa[2]*1000+aa[3]*100+aa[4]*10+aa[5];break;
case 7:sum[j++]=aa[0]*1000000+aa[1]*100000+aa[2]*10000+aa[3]*1000+aa[4]*100+aa[5]*10+aa[6];break;
case 8:sum[j++]=aa[0]*10000000+aa[1]*1000000+aa[2]*100000+aa[3]*10000+aa[4]*1000+aa[5]*100+aa[6]*10+aa[7];break;
*/
}
}
/****************************************************
液晶显示函数
******************************************************/
void lcd1602_display(uint count)
{
uchar a,b,c,d,e; //f,g,h;
a=count%10;
b=count/10%10;
c=count/100%10;
d=count/1000%10;
e=count/10000%10;
/* f=count/100000%10;
g=count/1000000%10;
h=count/10000000%10;
write_date(0x30+h);
write_date(0x30+g);
write_date(0x30+f);
*/
if(e!=0)
write_1602date(0x30+e);
if((e==0&&d!=0)||e!=0)
write_1602date(0x30+d);
if((e==0&&d==0&&c!=0)||e!=0||d!=0)
write_1602date(0x30+c);
if((e==0&&d==0&&c==0&&b!=0)||e!=0||d!=0||c!=0)
write_1602date(0x30+b);
write_1602date(0x30+a);
}
/*************************************************
运算结果函数并保存至 sum[k]
**************************************************/
void yunsuan()
{
uchar m;
for(k=0;bb[k]!=0&&k<10;k++) //先找出高级运算符运算
{
if(bb[k]=='*')
{
sum[k+1]=sum[k]*sum[k+1];
sum[k]='N';
}
if(bb[k]=='/')
{
sum[k+1]=sum[k]/sum[k+1];
sum[k]='N';
}
}
for(k=0;bb[k]!=0&&k<10;k++)
{
if(bb[k]=='+')
{
for(m=1;sum[k+m]=='N';)
{
m++;
}
sum[k+m]=sum[k]+sum[k+m];
}
if(bb[k]=='-')
{
for(m=1;sum[k+m]=='N';)
{
m++;
}
sum[k+m]=sum[k]-sum[k+m];
}
}
}
/*************************************************
main函数
***************************************************/
void main()
{
init_lcd1602();
while(1)
{
flag=0;
keyscan();
if(flag!=0)
{
if(num>=0&&num<=9)
{
aa[i++]=num;
write_1602date(0x30+num);
n++;
}
if(num=='+')
{
write_1602date(0x20+11);//1602 '+'符
bb[k++]=num;
zuan_shu();
for(i=0;i<n;i++)
aa[i]=0;[/i][i]
i=0;
n=0;
}
if(num=='-')
{
write_1602date(0x20+13);//1602 '-'符
bb[k++]=num;
zuan_shu();
for(i=0;i<n;i++)
aa[i]=0;[/i][i]
i=0;
n=0;
}
if(num=='*')
{
write_1602date(0x20+10);//1602 '*'符
bb[k++]=num;
zuan_shu();
for(i=0;i<n;i++)
aa[i]=0;[/i][i]
i=0;
n=0;
}
if(num=='/')
{
write_1602date(0xf0+13);//1602 '/'符
bb[k++]=num;
zuan_shu();
for(i=0;i<n;i++)
aa[i]=0;[/i][i]
i=0;
n=0;
}
if(num=='c'&&m==0) //删除一个数或一个运算符
{
write_1602com(0x04);//读或写后,指针减一,光标减一
write_1602date(' ');//1602 空符
write_1602com(0x06);//读或写后,指针加一,光标加一
if(n!=0)
{
n--;
aa[--i]=0;
}
else
{
bb[--k]=0;
}
}
if(num=='=')
{
m=1;
write_1602com(0xc0);
write_1602date(0x30+13);//1602 '='符
zuan_shu();
yunsuan();
count=sum[k];
lcd1602_display(count);
write_1602com(0x0c);
}
}
}
}
复制代码
全部资料51hei下载地址:
计算器.zip
(128.74 KB, 下载次数: 70)
2020-12-8 23:10 上传
点击文件名下载附件
计算器
下载积分: 黑币 -5
作者:
了解@
时间:
2020-12-9 00:26
因文章限制,全部资料在下面压缩包中........
欢迎光临 (http://www.51hei.com/bbs/)
Powered by Discuz! X3.1