⑴ 单片机简易计算器设计的程序
展开全部
首先会按键扫描,再会数码管或液晶屏显示,基本上可以了
程序
流程:
扫描按键(最多5次,最大65536,简易计算器吗)获得一个数,再扫描按键获得加减乘除符号
扫描按键获得另一个数
扫描按键获得“=”,显示计算结果
由于程序比较长,且与硬件有关,因此只贴出主程序:
void
main()
{
while(1)
{
c=1;
while(c<6)//输入第1个5
位数
{
keyval=keyscan();
if(keyval<10)
{
switch(c)
{
case
1:b1=keyval;
break;
case
2:b2=keyval;
break;
case
3:b3=keyval;
break;
case
4:b4=keyval;
break;
case
5:b5=keyval;
break;
}
c++;
}
display1(b1,b2,b3,b4,b5);
}
while(c==6)
//输入计算符号
{
keyval=keyscan();
if((keyval>=10)&&(keyval<14))
//10-13代表加减乘除
4种符号
{
d=keyval;
}
c=1;
display3(d);
}
while(c<6)
//输入第2个5
位数
{
keyval=keyscan();
if(keyval<10)
{
switch(c)
{
case
1:d1=keyval;
break;
case
2:d2=keyval;
break;
case
3:d3=keyval;
break;
case
4:d4=keyval;
break;//
除
case
5:d5=keyval;
break;
}
c++;
}
display2(d1,d2,d3,d4,d5);
}
bb=
b1*10000+b2*1000+b3*100+b4*10+b5;//5个按键数值合成一个数
dd=d1*10000+d1*1000+d3*100+d4*10+d5;
//另外5个按键数值也合成一个数
while(keyval!=14)
//等待按下"="
{
keyval=keyscan();
}
Delay1ms(10);
switch(d)
{
case
10:ee=bb+dd;
break;//+
case
11:
flag1=1;//结果是负数的标志,先假定是负数
if(bb>=dd)
{
ee=bb-dd;
//结果不是负数
flag1=0;
}
else
ee=dd-bb;
//减数和被减数交换
break;
case
12:ee=bb*dd;
break;//*可能会溢出
case
13:ee=bb/dd;
//除法小数部分会丢失,保留2位
ff=bb%dd;
fd1=ff*10/dd;
fd2=ff*100/dd%10;
break;
}
f10=ee/1000000000%10;
f9=ee/100000000%10;
f8=ee/10000000%10;
f7=ee/1000000%10;
f6=ee/100000%10;
f5=ee/10000%10;
f4=ee/1000%10;
f3=ee/100%10;
f2=ee/10%10;
f1=ee%10;
display4(f10,f9,f8,f7,f6,f4,f4,f3,f2,f1,fd1,fd2);
while(keyval!=15)
{
keyval=keyscan();
}
b1=0;b2=0;b3=0;b4=0;b5=0;
d1=0;d2=0;d3=0;d4=0;d5=0;
bb=0;dd=0;ee=0;
init2();
}
}
⑵ 单片机的简易计算器
单片机计算器
基本功能介绍:
简单的加减乘除的运算。
时间显示功能,而且能实现计算器模块和时间模块之间的任意切换。
按键音却换功能。
原理;
多功能单片机计算器是一个实现加减乘除的和时间功能的计算器,主要的硬件组成由,一个AT89s52单片机芯片,一个LED液晶(1602液晶),一个4*4键盘,和4个特殊功能按键。
一个时钟芯片(DS1302),一个蜂鸣器。
单个硬件模块个的介绍
AT89S52:
主要控制芯片,它是由8kflash,256BRAM,6个中断源,详情参考AT89S52的技术文档.
1602液晶
1602液晶模块内部的字符发生存储器(CGROM)已经存储了160个不同的点阵字符图形,这些字符有:阿拉伯数字、英文字母的大小写、常用的符号等,每一个字符都有一个固定的代码,比如大写的英文字母“A”的代码是01000001B(41H),显示时模块把地址41H中的点阵字符图形显示出来,我们就能看到字母“A”,而且可以实现一些复杂的字符操作:1:清显示,光标复位到地址00H位置,2:光标和显示模式设置 光标移动方向,高电平右移,低电平左移,屏幕上所有文字是否左移或者右移。高电平表示有效,低电平则无效 3:显示开关控制,控制整体显示的开与关,高电平表示开显示,低电平表示关显示,控制光标的开与关,高电平表示有光标,低电平表示无光标,控制光标是否闪烁,高电平闪烁,低电平不闪烁4:光标或显示移位,高电平时移动显示的文字,低电平时移动光标5:功能设置命令 DL:高电平时为4位总线,低电平时为8位总线 N:低电平时为单行显示,高电平时双行显示 F: 低电平时显示5x7的点阵字符,高电平时显示5x10的点阵字符(高低电平在相应的指令上实现),详情可参考1602的技术文档。
1602采用标准的16脚接口: 第1脚:VSS为地电源第2脚:VDD接5V正电源第3脚:V0为液晶显示器对比度调整端,接正电源时对比度最弱,接地电源时对比度最高,对比度过高时会产生“鬼影”,使用时可以通过一个10K的电位器调整对比度第4脚:RS为寄存器选择,高电平时选择数据寄存器、低电平时选择指令寄存器。第5脚:RW为读写信号线,高电平时进行读操作,低电平时进行写操作。当RS和RW共同为低电平时可以写入指令或者显示地址,当RS为低电平RW为高电平时可以读忙信号,当RS为高电平RW为低电平时可以写入数据。第6脚:E端为使能端,当E端由高电平跳变成低电平时,液晶模块执行命令。 第7~14脚:D0~D7为8位双向数据线。 第15~16脚:空脚。
1602液晶和单片机的接法
4*4键盘,和4个特殊功能按键
K(切换键) No(复位键)
(时间设置键) C(清除键) +
1 2 3 —
4 5 6 *
7 8 9 %(除)
—/+ 0 。 =
前4个为特殊功能键,
后十六个采用键盘扫描接法,
扫描原理:
首先给p3口赋11111110(0xfe),然后再读取p3口的值,如果为11101110(0xee)说明是第一排第一个被按下,如果是11011110(0xde)说明是第一排第二个被按下,如果是10111110(0xbe)说明是第一排第三个被按下,如果是0111110(0x7e)说明是第一排第四个被按下,
判断二三四排的按键,都采用同样的方法,只要分别给P3口赋不同的值即可,在读取p3口的值,在判断。用这样的方法即可实现4*4键盘的扫描,只要有键按下,就可以知道是那个键按下,通过这种方法可大大节省单片机的io口的资源。详情可参考网上的键盘扫描原理
时钟芯片(DS1302)
DS1302 是DALLAS 公司推出的涓流充电时钟芯片内含有一个实时时钟/日历和31 字节静态RAM ,通过简单的串行接口与单片机进行通信实时时钟/日历电路提供秒分时日日期月年的信息每月的天数和闰年的天数可自动调整时钟操作可通过AM/PM 指示决定采用24 或12 小时格式DS1302 与单片机之间能简单地采用同步串行的方式进行通信仅需用到三个口线1 RES 复位2 I/O 数据线3 SCLK串行时钟时钟/RAM 的读/写数据以一个字节或多达31 个字节的字符组方式
实时时钟具有能计算2100 年之前的秒分时日日期星期月年的能力还有闰年调整的能力(详情可参考DS1302的技术文档
管脚描述
X1 X2 32.768KHz 晶振管脚
GND 地
RST 复位脚
I/O 数据输入/输出引脚
SCLK 串行时钟
Vcc1,Vcc2 电源供电管脚
计算器工作大概流程
⑶ 大神,求51单片机做简易计算器的那个c语言程序
以下是我编的简易计算器程序,基本成功
//4*4键盘检测程序,按下键后相应的代码显示在液晶屏上
//显示5位后,第6次显示操作符号
//再显示下一个数
// 键值与功能对应表
//键值 0 1 2 3 4 5 6 7 8 9 10 11 12 13 14 15
//功能 0 1 2 3 4 5 6 7 8 9 + - × ÷ = 清零
#include<reg52.h>
sbit beep=P2^3;
sbit lcden=P3^4;
sbit rs=P3^5;
sbit rw=P3^6;
#define uint unsigned int
#define ulint unsigned long int
#define uchar unsigned char
#define lcddata P0
ulint bb,dd,ee,ff;
uchar d,flag1;
uchar fd1,fd2;
uchar b1=16,b2=16,b3=16,b4=16,b5=16;
uchar d1=16,d2=16,d3=16,d4=16,d5=16;
uchar f1=16,f2=16,f3=16,f4=16,f5=16,f6=16,f7=16,f8=16,f9=16,f10=16;
uchar key,keyval,c,temp;
void Delay1ms(uint i) //1ms延时程序
{
uint j;
for(;i>0;i--)
{
for(j=0;j<125;j++)
{;}
}
}
void write_com(uchar com)
{
lcddata=com;
rs=0;
rw = 0;
lcden=0;
Delay1ms(10);
lcden=1;
Delay1ms(10);
lcden=0;
}
void write_date(uchar date)
{
lcddata=date;
rs=1;
rw=0;
lcden=0;
Delay1ms(10);
lcden=1;
Delay1ms(10);
lcden=0;
}
void init2()
{
rw=0;
write_com(0x38);
Delay1ms(10);
write_com(0x0f);
Delay1ms(10);
write_com(0x06);
Delay1ms(10);
write_com(0x01);
Delay1ms(10);
}
void display1(uchar A1,uchar A2,uchar A3,uchar A4,uchar A5) //第1个数显示程序
{
init2();
write_com(0x80);//第1行,第1字
Delay1ms(10);
write_date(0x30+A1);
Delay1ms(10);
write_date(0x30+A2);
Delay1ms(10);
write_date(0x30+A3);
Delay1ms(10);
write_date(0x30+A4);
Delay1ms(10);
write_date(0x30+A5);
Delay1ms(10);
}
void display2(uchar A1,uchar A2,uchar A3,uchar A4,uchar A5) //第2个数显示程序
{
write_com(0x88);//第1行,第1字
Delay1ms(10);
write_date(0x30+A1);
Delay1ms(10);
write_date(0x30+A2);
Delay1ms(10);
write_date(0x30+A3);
Delay1ms(10);
write_date(0x30+A4);
Delay1ms(10);
write_date(0x30+A5);
Delay1ms(10);
}
void display3(uchar a) //操作符号显示程序
{
write_com(0x86);//第1行,第1字
Delay1ms(10);
switch(a)
{
case 10:
write_date('+');
Delay1ms(10);
case 11:
write_date('-');
Delay1ms(10);
case 12:
write_date('x');
Delay1ms(10);
case 13:
write_date('/');
Delay1ms(10);
}
}
void display4(uchar A1,uchar A2,uchar A3,uchar A4,uchar A5,uchar A6,uchar A7,uchar A8,uchar A9,uchar A10,uchar A11,uchar A12) //结果显示程序
{
write_com(0x80+0x40);//第2行,第1字
Delay1ms(10);
if (flag1==0)
{
write_date('-');
}
else write_date('+');
Delay1ms(10);
write_date(0x30+A1);
Delay1ms(10);
write_date(0x30+A2);
Delay1ms(10);
write_date(0x30+A3);
Delay1ms(10);
write_date(0x30+A4);
Delay1ms(10);
write_date(0x30+A5);
Delay1ms(10);
write_date(0x30+A6);
Delay1ms(10);
write_date(0x30+A7);
Delay1ms(10);
write_date(0x30+A8);
Delay1ms(10);
write_date(0x30+A9);
Delay1ms(10);
write_date(0x30+A10);
Delay1ms(10);
write_date('.');
Delay1ms(10);
write_date(0x30+A11);
Delay1ms(10);
write_date(0x30+A12);
Delay1ms(10);
}
uchar keyscan()
{
key=16;
P3=0xef;//P3.7输出1个低电平
temp=P3; //读取
temp=temp&0x0f;//屏蔽高4位
if(temp!=0x0f)
{
Delay1ms(10);
if(temp!=0x0f)
{
temp=P3;
switch(temp)
{
case 0xee:
key=0;
break;
case 0xed:
key=4;
break;
case 0xeb:
key=8;
break;
case 0xe7:
key=12;
break;
}
while(temp!=0x0f)
{
temp=P3;
temp=temp&0x0f;
beep=0;
}
beep=1;
}
}
P3=0xdf;
temp=P3;
temp=temp&0x0f;
if(temp!=0x0f)
{
Delay1ms(10);
if(temp!=0x0f)
{
temp=P3;
switch(temp)
{
case 0xde:
key=1;
break;
case 0xdd:
key=5;
break;
case 0xdb:
key=9;
break;
case 0xd7:
key=13;
break;
}
while(temp!=0x0f)
{
temp=P3;
temp=temp&0x0f;
beep=0;
}
beep=1;
}
}
P3=0xbf;
temp=P3;
temp=temp&0x0f;
if(temp!=0x0f)
{
Delay1ms(10);
if(temp!=0x0f)
{
temp=P3;
switch(temp)
{
case 0xbe:
key=2;
break;
case 0xbd:
key=6;
break;
case 0xbb:
key=10;
break;
case 0xb7:
key=14;
break;
}
while(temp!=0x0f)
{
temp=P3;
temp=temp&0x0f;
beep=0;
}
beep=1;
}
}
P3=0x7f;
temp=P3;
temp=temp&0x0f;
if(temp!=0x0f)
{
Delay1ms(10);
if(temp!=0x0f)
{
temp=P3;
switch(temp)
{
case 0x7e:
key=3;
break;
case 0x7d:
key=7;
break;
case 0x7b:
key=11;
break;
case 0x77:
key=15;
break;
}
while(temp!=0x0f)
{
temp=P3;
temp=temp&0x0f;
beep=0;
}
beep=1;
}
}
return(key);
}
void main()
{ while(1)
{
c=1;
while(c<6)//输入第1个5 位数
{
keyval=keyscan();
if(keyval<10)
{
switch(c)
{
case 1:b1=keyval; break;
case 2:b2=keyval; break;
case 3:b3=keyval; break;
case 4:b4=keyval; break;
case 5:b5=keyval; break;
}
c++;
}
display1(b1,b2,b3,b4,b5);
}
while(c==6) //输入计算符号
{
keyval=keyscan();
if((keyval>=10)&&(keyval<14)) //可去一层括号,因逻辑运算优先级较低
{
d=keyval;
}
c=1;
display3(d);
}
while(c<6) //输入第2个5 位数
{
keyval=keyscan();
if(keyval<10)
{
switch(c)
{
case 1:d1=keyval; break;
case 2:d2=keyval; break;
case 3:d3=keyval; break;
case 4:d4=keyval; break;// 除
case 5:d5=keyval; break;
}
c++;
}
display2(d1,d2,d3,d4,d5);
}
bb= b1*10000+b2*1000+b3*100+b4*10+b5;
dd=d1*10000+d1*1000+d3*100+d4*10+d5;
while(keyval!=14) //等待按下"="
{
keyval=keyscan();
}
Delay1ms(10);
switch(d)
{
case 10:ee=bb+dd; break;//+
case 11:
flag1=1;
if(bb>=dd)
{
ee=bb-dd; //-
flag1=0;
}
else ee=dd-bb;
break;
case 12:ee=bb*dd; break;//*可能会溢出
case 13:ee=bb/dd; //除法小数部分会丢失,保留2位
ff=bb%dd;
fd1=ff*10/dd;
fd2=ff*100/dd%10;
break;
}
f10=ee/1000000000%10;
f9=ee/100000000%10;
f8=ee/10000000%10;
f7=ee/1000000%10;
f6=ee/100000%10;
f5=ee/10000%10;
f4=ee/1000%10;
f3=ee/100%10;
f2=ee/10%10;
f1=ee%10;
display4(f10,f9,f8,f7,f6,f4,f4,f3,f2,f1,fd1,fd2);
while(keyval!=15)
{
keyval=keyscan();
}
b1=0;b2=0;b3=0;b4=0;b5=0;
d1=0;d2=0;d3=0;d4=0;d5=0;
bb=0;dd=0;ee=0;
init2();
}
}
⑷ 怎样用51单片机做计算器啊
1、硬件仿真图
4、程序源代码
#include <reg51.h>#include <intrins.h>
#include <ctype.h>
#include <stdlib.h>
#define uchar unsigned char
#define uint unsigned int
uchar operand1[9], operand2[9];
uchar operator;
void delay(uint);
uchar keyscan();
void disp(void);
void buf(uint value);
uint compute(uint va1,uint va2,uchar optor);
uchar code table[] = {0xc0,0xf9,0xa4,0xb0,0x99,
0x92,0x82,0xf8,0x80,0x90,0xff};
uchar dbuf[8] = {10,10,10,10,10,10,10,10};
void delay(uint z)
{
uint x,y;
for(x=z;x>0;x--)
for(y=110;y>0;y--);
}
uchar keyscan()
{
uchar skey;
P1 = 0xfe;
while((P1 & 0xf0) != 0xf0)
{
delay(3);
while((P1 & 0xf0) != 0xf0)
{
switch(P1)
{
case 0xee: skey = '7'; break;
case 0xde: skey = '8'; break;
case 0xbe: skey = '9'; break;
case 0x7e: skey = '/'; break;
default: skey = '#';
}
while((P1 & 0xf0) != 0xf0)
;
}
}
P1 = 0xfd;
while((P1 & 0xf0) != 0xf0)
{
delay(3);
while((P1 & 0xf0) != 0xf0)
{
switch(P1)
{
case 0xed: skey = '4'; break;
case 0xdd: skey = '5'; break;
case 0xbd: skey = '6'; break;
case 0x7d: skey = '*'; break;
default: skey = '#';
}
while((P1 & 0xf0) != 0xf0)
;
}
}
P1 = 0xfb;
while((P1 & 0xf0) != 0xf0)
{
delay(3);
while((P1 & 0xf0) != 0xf0)
{
switch(P1)
{
case 0xeb: skey = '1'; break;
case 0xdb: skey = '2'; break;
case 0xbb: skey = '3'; break;
case 0x7b: skey = '-'; break;
default: skey = '#';
}
while((P1 & 0xf0) != 0xf0)
;
}
}
P1 = 0xf7;
while((P1 & 0xf0) != 0xf0)
{
delay(3);
while((P1 & 0xf0) != 0xf0)
{
switch(P1)
{
case 0xe7: skey = '$'; break;
case 0xd7: skey = '0'; break;
case 0xb7: skey = '='; break;
case 0x77: skey = '+'; break;
default: skey = '#';
}
while((P1 & 0xf0) != 0xf0)
;
}
}
return skey;
}
void main()
{
uint value1, value2, value;
uchar ckey, cut1 = 0, cut2 = 0;
uchar operator;
uchar i, bool = 0;
init:
buf(0);
disp();
value = 0;
cut1 = cut2 = 0;
bool = 0;
for(i = 0;i < 9;i++)
{
operand1[i] = '