




已阅读5页,还剩11页未读, 继续免费阅读
版权说明:本文档由用户提供并上传,收益归属内容提供方,若内容存在侵权,请进行举报或认领
文档简介
/*修改版程序功能:实现简单计算器,可以实现多个数字的加减乘除运算。不足点:乘法的话,最高可至255*255。减法没有实现负数。除法,小数点后都去除,只留下整数。建议:最好实现3位数的运算,超过的话,运算出现错误。*/#include #define uchar unsigned char#define uint unsigned intuchar code table_dul=0x3f,0x06,0x5b,0x4f, 0x66,0x6d,0x7d,0x07,0x7f,0x6f;uchar code table_wei=0xfe,0xfd,0xfb,0xf7,0xef,0xdf,0xbf,0x7f;sbit dula=P26;sbit wela=P27;uint a,b,c;uint num;uchar flag,flag1;void display(uint num); /*延时函数*/void delay(uint z)uint x,y;for(x=z;x0;x-)for(y=110;y0;y-);/*检测函数*/识别是哪个操作键按下,并标记究竟要做何种操作/flag为1,则说明是按下“+”;flag为2,则说明按下“-”;flag为3,则说明按下“*”;flag为4,则说明按下“/”void jiance()switch(flag) case 1:flag1=1;break;case 2:flag1=2;break;case 3:flag1=3;break;case 4:flag1=4;break;flag=0;c=1;/判断是否已经按过一次功能键了/*计算函数*/flag1为1则加,为2则减,为3则乘,为4则除。void jisuan(uint a,uint b)switch(flag1)case 1:num=0;num=a+b;break;case 2:num=0;num=a-b;break;case 3:num=0;num=a*b;break;case 4:num=0;num=a/b;break;flag1=0;c=1;/判断是否已经按过一次功能键了 /*键盘扫描*/*键盘布局 1 2 3 +4 5 6 -7 8 9 * 0 = 清零 / */void keyscan()uchar temp,key;P3=0Xfe;temp=P3;temp=temp&0xf0;if(temp!=0xf0)delay(10);temp=P3;temp=temp&0xf0;if(temp!=0xf0)temp=P3;switch(temp)case 0xee:if(c=1)c=0;num=0;key=1;num=num*10+key;break;/如果按键“=”按下过,则num清零。case 0xde:if(c=1)c=0;num=0;key=2;num=num*10+key;break;case 0xbe:if(c=1)c=0;num=0;key=3;num=num*10+key;break;case 0x7e:/*判断是否是第一次按下运算键, 如果是,则直接把num赋给a,如果不是,则判断上次按下的是什么运算键,则进行对应操作*/if(a=0)a=num;else switch(flag1)case 1:a=a+num;num=a;break;case 2:a=a-num;num=a;break;case 3:a=a*num;num=a;break;case 4:a=a/num;num=a;break; flag=1;jiance();break;/+while(temp!=0xf0) temp=P3;temp=temp&0xf0;display(num);P3=0Xfd;temp=P3;temp=temp&0xf0;if(temp!=0xf0)delay(10);temp=P3;temp=temp&0xf0;if(temp!=0xf0)temp=P3;switch(temp)case 0xed:if(c=1)c=0;num=0;key=4;num=num*10+key;break;case 0xdd:if(c=1)c=0;num=0;key=5;num=num*10+key;break;case 0xbd:if(c=1)c=0;num=0;key=6;num=num*10+key;break;case 0x7d:if(a=0)a=num;else switch(flag1)case 1:a=a+num;num=a;break;case 2:a=a-num;num=a;break;case 3:a=a*num;num=a;break;case 4:a=a/num;num=a;break; flag=2;jiance();break; /-while(temp!=0xf0) temp=P3;temp=temp&0xf0;display(num);P3=0Xfb;temp=P3;temp=temp&0xf0;if(temp!=0xf0)delay(10);temp=P3;temp=temp&0xf0;if(temp!=0xf0)temp=P3;switch(temp)case 0xeb:if(c=1)c=0;num=0;key=7;num=num*10+key;break;case 0xdb:if(c=1)c=0;num=0;key=8;num=num*10+key;break;case 0xbb:if(c=1)c=0;num=0;key=9;num=num*10+key;break;case 0x7b:if(a=0)a=num;else switch(flag1)case 1:a=a+num;num=a;break;case 2:a=a-num;num=a;break;case 3:a=a*num;num=a;break;case 4:a=a/num;num=a;break; flag=3;jiance();break;/*while(temp!=0xf0) temp=P3;temp=temp&0xf0;display(num);P3=0Xf7;temp=P3;temp=temp&0xf0;if(temp!=0xf0)delay(10);temp=P3;temp=temp&0xf0;if(temp!=0xf0)temp=P3;switch(temp)case 0xe7:if(c=1)c=0;num=0;key=0;num=num*10+key;break;case 0xd7:b=num;jisuan(a,b);a=0;b=0;break;/=case 0xb7:num=0;break; /清零case 0x77:if(a=0)a=a=num;elseswitch(flag1)case 1:a=a+num;num=a;break;case 2:a=a-num;num=a;break;case 3:a=a*num;num=a;break;case 4:a=a/num;num=a;break; flag=4;jiance();break;/while(temp!=0xf0) temp=P3;temp=temp&0xf0;display(num); /*显示函数*/void display(uint num)uchar wan,qian,bai,shi,ge;wan=num/10000;qian=num%10000/1000;bai=num%1000/100;shi=num%100/10;ge=num%10;/下面判断是否最高位为0,如果为0,则不显示最高位。依次判断下去。if(wan=0)if(qian=0)if(bai=0)if(shi=0)dula=1;P0=table_dulge;dula=0;P0=0XFF;wela=1;P0=table_wei5;wela=0;delay(3);elsedula=1;P0=table_dulshi;dula=0;P0=0XFF;wela=1;P0=table_wei4;wela=0;delay(3);dula=1;P0=table_dulge;dula=0;P0=0XFF;wela=1;P0=table_wei5;wela=0;delay(3);elsedula=1;P0=table_dulbai;dula=0;P0=0XFF;wela=1;P0=table_wei3;wela=0;delay(3);dula=1;P0=table_dulshi;dula=0;P0=0XFF;wela=1;P0=table_wei4;wela=0;delay(3);dula=1;P0=table_dulge;dula=0;P0=0XFF;wela=1;P0=table_wei5;wela=0;delay(3);elsedula=1;P0=table_dulqian;dula=0;P0=0XFF;wela=1;P0=table_wei2;wela=0;delay(3);dula=1;P0=table_dulbai;dula=0;P0=0XFF;wela=1;P0=table_wei3;wela=0;delay(3);dula=1;P0=table_dulshi;dula=0;P0=0XFF;wela=1;P0=table_wei4;wela=0;delay(3);dula=1;P0=table_dulge;dula=0;P0=0XFF;wela=1;P0=table_wei5;wela=0;delay(3);else dula=1;P0=table_dulwan;dula=0;P0=0XFF;wela=1;P0=table_wei1;wela=0;delay(3);dula=1;P0=table_dulqian;dula=0;P0=0XFF;wela=1;P0=table_wei2;wela=0;delay(3);dula=1;P0=table_dulbai;dula=0;P0=0XFF;wela=1;P0=table_wei3;wela=0;delay(3);dula=1;P0=table_dulshi;dula=0;P0=0XFF;wela=1;P0=table_wei4;wela=0;delay(3);dula=1;P0=table_dulge;dula=0;P0=0XFF;wela=1;P0=table_wei5;wela=0;delay(3); /*主函数*/void main()while(1) keyscan();display(num); /*/简单计算器(数码管)程序分析:首先明确按键位置;利用4x4矩阵键盘,我做了如下位置的设定:第一列第二列第三列第四列第一行123+第二行456-第三行789*第四行0=清屏/之前我们也已经教过了键盘扫描,这里我们就不赘述了。当然我们也写过了4x4独立按键实现016的程序。下面我们就看一下键盘扫描函数,并分析一下不同点,以及这其中的写计算器的重难点。现在看到这里,switch(temp)case 0xee:if(c=1)c=0;num=0;key=1;num=num*10+key;break;/如果按键“=”按下过,则num清零。case 0xde:if(c=1)c=0;num=0;key=2;num=num*10+key;break;case 0xbe:if(c=1)c=0;num=0;key=3;num=num*10+key;break;case 0x7e:/*判断是否是第一次按下运算键,如果是,则直接把num赋给a,如果不是,则判断上次按下的是什么运算键,则进行对应操作*/if(a=0)a=num;else switch(flag1)case 1:a=a+num;num=a;break;case 2:a=a-num;num=a;break;case 3:a=a*num;num=a;break;case 4:a=a/num;num=a;break; flag=1;jiance();break;/+我们可以发现,跟之前我们写过的程序十分相似,只是多了if(c=1)c=0;num=0;和num=num*10+key;还有就是表明加号键的跟其他的不一样。下面我们就慢慢一个个解决。之前我们写的那个1到16通过按键显示的程序,是不是当重新按下另一个键时,之前按下的数据就会被清空,但是我们这次要做的计算器,这样明显是不行的。就好比我第一次按下1,再按下2,则说明我输入的这个数是12。所以,我们这里就利用num=num*10+key;实现数据的保存。一开始num默认为0,当按下1时,key=1,则num=0*10+1=1;当再次按下2时,num已经变成1,key=2,则num=1*10+2=12;这样就解决了其中一个问题。至于这个if(c=1)c=0;num=0;问题,我们会在待会的讲解中解释的。现在假如我们已经输入了第一个数123,那么当我们按下运算键(即+-*/=)时,我们要该怎么做呢。首先我们要做的第一步,判断是否第一次按下运算键,如果是第一次按下,那么a默认情况下, a就是0;如果不是第一次,那么,a就不为0。如果是第一次按下,则完成数据存储,通过a=num,实现。如果a不等于0,则判断前一次按下的是哪一个键,这个通过flag1,来判断,最后把a赋给num,让它显示出计算结果,完成对应的操作。第二步就是要知道按下的是什么运算键,这里我们可以通过标志位来解决。我们可以利用多个标志位来实现标示,但是这样明显会浪费资源。所以我们就利用flag来标示,当按下不同功能键(这里不包括=号),时,用不同数值表示。flag为1,则说明是按下“+”;flag为2,则说明按下“-”;flag为3,则说明按下“*”;flag为4,则说明按下“/”。之后,我们再通过检测函数jiance();检测是哪个运算键按下,并用flag1进行标志。下面这个就是检测函数void jiance()switch(flag) case 1:flag1=1;break;/加case 2:flag1=2;break;/减case 3:flag1=3;break;/乘case 4:flag1=4;break;/除flag=0;c=1;/判断是否已经按过一次功能键了检测函数通过c来标志是否按下运算键,当然在那个计算函数那里也有,C=1,则表明已经有功能键按下过。大家是否联系到刚才那个if(c=1)c=0;num=0;,通过这一个c。单片机就知道你是否按过功能键了。这样再次按下新的数字,num就被清零,这样就不会受到之前那个数的干扰了。假设我们要运算的数字已经输入完毕了,输入完最后一个数字,接下来我们要按的就是“=”键。而按下“=”键,那么接下来要做的便是计算函数了。下面是计算函数(如果是多个数的加减乘除,其实在之前的运算键中已经有运算了一部分,计算函数只是实现最后一个数与之前运算完的数进行最后一次运算并显示)void jisuan(uint a,uint b)switch(flag1)case 1:num=0;num=a+b;break;case 2:num=0;num=a-b;break;case 3:num=0;num=a*b;break;case 4:num=0;num=a/b;break;flag1=0;c=1;/判断是否已经按过一次功能键了 这个跟刚才那个判断功能键是否已经按下过一次很像,不同点就是它运算完的数是要显示出来,而那个判断功能键是否已经按下过一次的是把运算完的数据继续存储起来。但是num在之前已经有了数值,所以在判断完之后,就把num清零,避免后期运算的干扰。而且把num=0,放在这里也有一个原因。如果把num=0,放在判断之前,那么如果连续按下两次“=”,那么第二次按下,就只显示0了。这是因为在第一次运算完计算函数之后,就把flag1置为0了。那么就没办法进入判断。那么num就为0,就会显示0了。但是如果放在判断里面,那么再次按下“=”键,没进入判断语句,所以num不会被清零,就继续显示第一次运算完的数值了。接下来就清屏,这
温馨提示
- 1. 本站所有资源如无特殊说明,都需要本地电脑安装OFFICE2007和PDF阅读器。图纸软件为CAD,CAXA,PROE,UG,SolidWorks等.压缩文件请下载最新的WinRAR软件解压。
- 2. 本站的文档不包含任何第三方提供的附件图纸等,如果需要附件,请联系上传者。文件的所有权益归上传用户所有。
- 3. 本站RAR压缩包中若带图纸,网页内容里面会有图纸预览,若没有图纸预览就没有图纸。
- 4. 未经权益所有人同意不得将文件中的内容挪作商业或盈利用途。
- 5. 人人文库网仅提供信息存储空间,仅对用户上传内容的表现方式做保护处理,对用户上传分享的文档内容本身不做任何修改或编辑,并不能对任何下载内容负责。
- 6. 下载文件中如有侵权或不适当内容,请与我们联系,我们立即纠正。
- 7. 本站不保证下载资源的准确性、安全性和完整性, 同时也不承担用户因使用这些下载资源对自己和他人造成任何形式的伤害或损失。
最新文档
- 2025年产品运营初级面试攻略与模拟题答案
- 2025年产品经理高级面试指南面试模拟题与答案全解析
- 2025年人工智能算法实战教程与编程模拟题集
- 2025年农村电商发展现状及趋势分析面试题集萃
- 2025年上海国际新能源研究中心横向技术合同审批表
- 2025年国际商务礼仪与文化实战教程及模拟题集
- 2025年客户服务经理中级面试宝典高频问题预测与答案
- 2025年IT技术支持高级职位面试指南与模拟题集萃
- 2025年中国传统乐器演奏师认证考试题库
- 汽车钣金理论知识试题(及答案)
- 沟通与协调能力考核题库600题(答案)
- 危重患者血糖管理专家共识解读
- 工程缺陷责任期终止证书版本
- GB/T 45356-2025无压埋地排污、排水用聚丙烯(PP)管道系统
- 石墨产品的国际市场推广策略
- ktv店长合同范本
- 科技辅导员培训课件
- 小学生爱国主义教育工作计划
- 电子政务教程(第三版)课件全套 赵国俊 第1-12章 电子政务概要-中国电子政务的发展基础
- 乡镇卫生院医用耗材监管制度
- 语言学概论-第三章-语义
评论
0/150
提交评论