基于单片机的计算器的论文Word格式文档下载.docx
《基于单片机的计算器的论文Word格式文档下载.docx》由会员分享,可在线阅读,更多相关《基于单片机的计算器的论文Word格式文档下载.docx(36页珍藏版)》请在冰豆网上搜索。
图2-4、下载口电路原理图
三、程序流程图
主程序流程图
显示程序流程图
键扫程序流程图
3.1、程序清单
程序清单见附录4。
产品使用说明
该产品16个按键作为输入信号,液晶为显示器,按键功能如下图所示。
0~9为数字键,其中0~3有第二功能,一个小数点键,一个等号键,该键为四功能键,四个运算符号键。
通电后显示器显示万年历、星期和脑钟,此时按0键可进行校时,可看到时钟已停,并且秒在闪烁,此时按1键可使秒加一,按2键可使秒减一,把秒设定好后,再按0键,秒停止闪烁,分开始闪烁,此时按1键和2键同样可对分进行修改,然后依次时、日、月、年、以及闹钟的秒、分、时进行修改,然后再按0键时钟恢复走时,万年历和闹钟的校准就完成啦。
如果要使用计算器功能,则直接按3键即可进入计算器模式,等号键单键为“=”,双键为清除,默认计算类型为加减乘除,若要进行其他类型的计算,则可使用等号键三键,然后选择运算类型进行运算,此时符号键所对应的运算符号也有相应的变化。
该计算器的计算功能可实现加减乘除、正弦余弦正切余切、反正弦反余弦反正切反余切、平方、立方、m的k次方(m和k均由键盘输入)、e为底的m次方、自然对数、常用对数、开平方根。
可谓功能齐全,操作简单,给使用带来极大方便。
设计体会
在这次设计中使我对步进机有了更深的了解,对单片机也有了更高成次的了解,单片机的种类多,而型号杂,也是我们学习中的困难,所以就MCS—51系列的产品来说,就是一个典型的学习方法。
单片机编程是用汇编语言进行编程,也就需要我们对电路的分析,然后总结,查阅相关资料才能变成好的程序,编程讲究的是多动手写,自己写,用自己的思路,不怕写错,写错再改,懂得有新的思想这样才能提高。
在这次单片机应用系统设计中遇到到很大的困难,主要原因是平时的知识掌握的不够,通过查阅很多资料和类似的论文,才做成的。
以前也做过不少单片机设计,但面对这次设计,似乎也有一点束手五册了。
在这次的设计中,让我们发自内心的明白了以下这几个道理。
其实,这几个道理以前我们就懂,就知道,甚至每个人都知道,但真正到了关键时间,我们还会不会遵循它来办事就是一个问号啦。
书读百遍,其义自现。
三个臭皮匠胜过一个诸葛亮。
团结就是力量。
温故而知新。
正因为我开始没有遵循这几个道理所以在设计中走了不少弯路,表现出来了我很多的不足之处,就因为这样我们才会在这次设计中有进步、有发展,同时使自己的能力得到进一步的提升。
我将好好地记录下这次设计的点点滴滴,我想,这不单是我的经历,更是我的一笔财富。
参考文献
(1)李广弟《单片机原理及应用》北京航天航空大学出版社2008.2
(2)潘新民《微型计算机控制技术》电子工业出版社2008.5
(3)梅丽凤《单片机原理及接口技术》清华大学出版社2004.6
(4)李陪金《C语言程序设计案例教程》西安电子科技大学出版社2008.1
(5)戴佳《51单片机C语言应用程序设计实例精讲》电子工业出版社2006.4
(6)谭浩强《C程序设计》清华大学出版社
附录1、元器件清单
名称
型号
参数
数量
单片机
AT89S52
2
液晶
SBY12864Z-ZK3
一块
双12V变压器
1
发光二极管
LED
3
二极管
IN4001
8
三极管
9013,9014
4,8
稳压管
7805
排阻
10K*8
电阻
若干
晶振
11.0592MHz
下载口
电源接口
电解电容
100μf
470μf
4
电容
104
30
0.1μf
30pf
4
插座
单片机插座
所存器插座
40引脚,
24引脚
开关
按键
普通按键
12
排针排座
附录2、系统原理图
原理图
附录3、程序清单
#include<
reg52.h>
stdio.h>
intrins.h>
math.h>
#defineucharunsignedchar
#defineuintunsignedint
#defineulongunsignedlong
sbitrs=P2^0;
sbitrw=P2^1;
sbiten=P2^2;
sbitpsb=P2^3;
sbitret=P2^5;
sbitrd=P3^7;
sbits=P1^0;
sbits1=P1^4;
sbits2=P1^5;
sbits3=P1^6;
sbits4=P1^7;
ucharcount,s1num;
unsignedintnin,ss;
charyue,re,qi,shi,fen,miao;
uchardshi,dfen,dmiao,ling,aa,t1,p;
ucharcommand,data0,data1,data2,com0,j,l;
unsignedcharcommand,data1,data2,com0,bb,bb0,aa,cc,i,yun;
//
ucharlcdH,lcdL,key;
floatds,m,k;
ulongds0;
bitflag,flag1,flag2,flag3,flag4;
uchardisbuf[9]={0};
//定义显示缓冲区//
ucharcodetable[]={0x30,0x31,0x32,0x33,0x34,0x35,0x36,0x37,0x38,0x39,0x2e};
ucharcodetable1[]={0xc8,0xd5,0xd2,0xbb,0xb6,0xfe,0xc8,0xfd,0xcb,0xc4,0xce,0xe5,0xc1,0xf9};
//日~六//
ucharcodetable2[]={0x32,0x30,0x30,0x39,0xc4,0xea,0x30,0x35,0xd4,0xc2,0x30,0x31,0xc8,0xd5};
//年月日//
ucharcodetable4[]={0xd0,0xc7,0xc6,0xda,0xc1,0xf9};
//星期六//
ucharcodetabping[]={32,29,32,31,32,31,32,32,31,32,31,32};
ucharcodetabrun[]={32,30,32,31,32,31,32,32,31,32,31,32};
ucharcodexing1[]={3,6,0,3,5,1,3,6,2,4,0,2};
ucharcodexing2[]={4,0,0,3,5,1,3,6,2,4,0,2};
ucharxing[12]={0};
uchartab[12]={0};
//延时//
voiddelay(uintms)//延时250us
{
uchari;
while(ms--)
{
for(i=0;
i<
125;
i++);
}
}
//LCD初始化//
voidlcd_int()
ret=0;
delay(3);
ret=1;
_nop_();
psb=1;
//将PSB置1,通信方式为8BIT数据并口//
//写指令程序//
voidwrite_command(ucharcommand)
rs=0;
rw=0;
P0=command;
en=1;
en=0;
//写数据程序//
voidwrite_data(uchardata0)
{
rs=1;
P0=data0;
//LCD功能设置//
voidlcd_set()
command=0x30;
//基本指令集//
write_command(command);
command=0x01;
command=0x06;
command=0x0c;
//清屏程序//
voidclear_lcd()
command=0x34;
voiddisplay()
command=com0;
data2=lcdH;
write_data(data2);
data1=lcdL;
write_data(data1);
voiddisplay1(uchary,ucharx,uchar*p)
switch(y)
{
case1:
write_command(0x7f+x);
break;
//液晶第一行
case2:
write_command(0x8f+x);
//0x90+(x-1)
case3:
write_command(0x87+x);
break;
case4:
write_command(0x97+x);
default:
while(*p)
write_data(*p++);
voidxiaoshu()//先判断k是否为小数,如果k为小数,就将k转化为小数//
uintmg=1;
if(flag1)
cc;
i++)mg*=10;
k=k/(mg*1.0);
cc=0;
flag1=0;
//键扫描程序//
ucharkeyscan()
{ucharscancode,tmpcode;
P1=0xf0;
//行全为0
if((P1&
0xf0)!
=0xf0)//有键按下
{delay(100);
//延时去抖动
=0xf0)//判是否真的有键按下
{scancode=0xfe;
//诼行扫描
while((scancode&
0x10)!
=0)
{P1=scancode;
if((P1&
=0xf0)//本行有键按下
{tmpcode=(P1&
0xf0)|0x0f;
//返回特征字节码,为1的位即对应于行和列
return((~scancode)+(~tmpcode));
}
elsescancode=(scancode<
<
1)|0x01;
//行扫描码左移一位
return(0);
//无键按下,返回值为0
}
disjia()
com0=0x83;
lcdH=0xbc;
lcdL=0xd3;
display();
com0++;
lcdH=0xb7;
lcdL=0xa8;
com0=0x87;
disjian()
lcdL=0xf5;
discheng()
lcdH=0xb3;
lcdL=0xcb;
dischu()
lcdL=0xfd;
voidjishu()//把ds0处理后放入显示缓冲区中//
disbuf[0]=ds0/1000000000%10;
disbuf[1]=ds0/100000000%10;
disbuf[2]=ds0/10000000%10;
disbuf[3]=ds0/1000000%10;
disbuf[4]=ds0/100000%10;
disbuf[5]=ds0/10000%10;
disbuf[6]=ds0/1000%10;
disbuf[7]=ds0/100%10;
disbuf[8]=ds0/10%10;
disbuf[9]=ds0%10;
voiddisds()
com0=0x98;
for(i=0;
10;
i++)
if(i%2==0){com0++;
write_command(com0);
write_data(table[disbuf[i]]);
flag=0;
com0=0x88;
lcdH=0x20;
lcdL=0x20;
16;
i++){display();
com0++;
zhixing()//计算//
xiaoshu();
if(bb0==1)
switch(bb)
{
case1:
ds=m+k;
m=ds;
k=0;
case2:
ds=m-k;
case3:
ds=m*k;
case4:
ds=m/k;
default:
}
elseif(bb0==2)
{
m=m*3.1415926536;
m=m/180.0;
ds=sin(m);
ds=cos(m);
ds=tan(m);
ds=1.0/tan(m);
elseif(bb0==3)
ds=asin(m);
ds=ds*180.0;
ds=ds/3.1415926536;
ds=acos(m);
ds=atan(m);
ds=1.0/atan(m);
elseif(bb0==4)
ds=m*m;
//平方//
ds=m*m*m;
//立方///
ds=1;
for(i=0;
k;
i++)ds=ds*m;
//m的k次方//
ds=exp(m);
//e的m次方//
elseif(bb0==5)
ds=log(m);
//自然对数//
ds=log10(m);
///常用对数//
ds=sqrt(m);
//开方//
if(ds<
0)display1(4,1,"
-"
);
elsedisplay1(4,1,"
+"
if(ds>
4294967295)
clear_lcd();
display1(1,3,"
得数大于"
display1(2,2,"
二的三十二次方"
display1(4,2,"
请你按复位键"
delay(65000);
ds0=ds;
if((ds>
ds0))
if(ds<
1000){ds0=ds*1000000;
jishu();
disbuf[9]=disbuf[8];
disbuf[8]=disbuf[7];
disbuf[7]=disbuf[6];
disbuf[6]=disbuf[5];
disbuf[5]=disbuf[4];
disbuf[4]=10;
elseif(ds<
10000){ds0=ds*100000;
disbuf[5]=10;
100000){ds0=ds*10000;
disbuf[6]=10;
1000000){ds0=ds*1000;
disbuf[7]=10;
10000000){ds0=ds*100;
disbuf[8]=10;
elsejishu();
disds();
voidjiemian1()
display1(1,1,"
请按所选类型序号"
if(!
yun)
display1(2,2,"
0加减乘除"
display1(3,2,"
1弦切值"
display1(4,2,"
2反弦切值"
elseif(yun==1)
3幂运算"
else
4对数、开方运算"
voidjiemian2()
display1(2,3,"
下面进行"
switch(bb0)
display1(3,2,"
加减乘除运算"
弦切值运算"
反弦切值运算"
幂运算"
case5: