51单片机简易计算器两个四位数码管代码
时间: 2023-11-28 08:51:06 浏览: 120
基于51单片机的简单计算器(数码管显示,附仿真图)
5星 · 资源好评率100%
以下是使用 51 单片机实现的简易计算器代码,可以在两个四位数码管上显示计算结果。其中,使用了按键输入和数码管显示的库函数,需要根据实际情况进行更改。
```c
#include <reg52.h>
#include <intrins.h>
#include "key.h" // 按键输入库函数
#include "led.h" // 数码管显示库函数
#define uchar unsigned char
#define uint unsigned int
uchar flag = 0; // 操作符标志位,0:加法,1:减法,2:乘法,3:除法
uchar num1[4] = {0}; // 第一个操作数
uchar num2[4] = {0}; // 第二个操作数
uchar result[4] = {0}; // 计算结果
// 数码管显示函数
void show(uchar *num)
{
uchar i;
for (i = 0; i < 4; i++)
{
LED8_DIO = 1; // 选择第一个数码管
LED8_DCLK = 0; // 指令锁存
LED8_DCLK = 1;
LED8_DIO = num[i]; // 数据输入
LED8_DCLK = 0; // 数据锁存
LED8_DCLK = 1;
LED7_DIO = 1; // 选择第二个数码管
LED7_DCLK = 0; // 指令锁存
LED7_DCLK = 1;
LED7_DIO = num[i]; // 数据输入
LED7_DCLK = 0; // 数据锁存
LED7_DCLK = 1;
delay_ms(1); // 延时1ms,使数码管显示更加稳定
}
}
// 数码管清零函数
void clear()
{
uchar i;
for (i = 0; i < 4; i++)
{
num1[i] = 0;
num2[i] = 0;
result[i] = 0;
}
}
// 加法运算函数
void add()
{
uchar i, j, k = 0;
for (i = 3; i >= 0; i--)
{
result[i] = num1[i] + num2[i] + k;
k = result[i] / 10;
result[i] %= 10;
}
}
// 减法运算函数
void sub()
{
uchar i, j, k = 0;
for (i = 3; i >= 0; i--)
{
result[i] = num1[i] - num2[i] - k;
if (result[i] < 0)
{
result[i] += 10;
k = 1;
}
else
{
k = 0;
}
}
}
// 乘法运算函数
void mul()
{
uchar i, j, k;
uchar temp[8] = {0};
for (i = 0; i < 4; i++)
{
k = 0;
for (j = 0; j < 4; j++)
{
temp[i + j] += num1[i] * num2[j] + k;
k = temp[i + j] / 10;
temp[i + j] %= 10;
}
temp[i + 4] += k;
}
for (i = 0; i < 4; i++)
{
result[i] = temp[i];
}
}
// 除法运算函数
void div()
{
uchar i, j, k;
uchar temp[4] = {0};
for (i = 0; i < 4; i++)
{
for (j = 9; j >= 0; j--)
{
temp[i] = j;
mul();
if (result[0] == num1[3] && result[1] == num1[2] && result[2] == num1[1] && result[3] <= num1[0])
{
num1[0] -= result[3];
num1[1] -= result[2];
num1[2] -= result[1];
num1[3] -= result[0];
break;
}
}
result[i] = temp[i];
}
}
void main()
{
uchar i, j;
clear(); // 数码管清零
while (1)
{
if (flag == 0) // 加法运算
{
for (i = 0; i < 4; i++)
{
num1[i] = keyscan(); // 输入第一个操作数
show(num1); // 显示第一个操作数
}
for (i = 0; i < 4; i++)
{
num2[i] = keyscan(); // 输入第二个操作数
show(num2); // 显示第二个操作数
}
add(); // 进行加法运算
show(result); // 显示结果
flag = 4; // 标志位复位
}
else if (flag == 1) // 减法运算
{
for (i = 0; i < 4; i++)
{
num1[i] = keyscan(); // 输入第一个操作数
show(num1); // 显示第一个操作数
}
for (i = 0; i < 4; i++)
{
num2[i] = keyscan(); // 输入第二个操作数
show(num2); // 显示第二个操作数
}
sub(); // 进行减法运算
show(result); // 显示结果
flag = 4; // 标志位复位
}
else if (flag == 2) // 乘法运算
{
for (i = 0; i < 4; i++)
{
num1[i] = keyscan(); // 输入第一个操作数
show(num1); // 显示第一个操作数
}
for (i = 0; i < 4; i++)
{
num2[i] = keyscan(); // 输入第二个操作数
show(num2); // 显示第二个操作数
}
mul(); // 进行乘法运算
show(result); // 显示结果
flag = 4; // 标志位复位
}
else if (flag == 3) // 除法运算
{
for (i = 0; i < 4; i++)
{
num1[i] = keyscan(); // 输入第一个操作数
show(num1); // 显示第一个操作数
}
for (i = 0; i < 4; i++)
{
num2[i] = keyscan(); // 输入第二个操作数
show(num2); // 显示第二个操作数
}
div(); // 进行除法运算
show(result); // 显示结果
flag = 4; // 标志位复位
}
else // 等待操作符输入
{
switch (keyscan())
{
case 0x0d: // 加法
flag = 0;
break;
case 0x0c: // 减法
flag = 1;
break;
case 0x0b: // 乘法
flag = 2;
break;
case 0x0a: // 除法
flag = 3;
break;
default:
break;
}
delay_ms(10); // 延时10ms,避免按键抖动
}
}
}
```
其中,按键输入和数码管显示的库函数代码如下:
```c
// 按键输入库函数
#ifndef __KEY_H__
#define __KEY_H__
#include <reg52.h>
#include <intrins.h>
#define uchar unsigned char
#define uint unsigned int
sbit KEY1 = P1 ^ 0;
sbit KEY2 = P1 ^ 1;
sbit KEY3 = P1 ^ 2;
sbit KEY4 = P1 ^ 3;
// 延时函数,约10us
void delay_10us()
{
_nop_();
_nop_();
_nop_();
_nop_();
_nop_();
}
// 检测按键是否按下
uchar keydown()
{
if (KEY1 == 0 || KEY2 == 0 || KEY3 == 0 || KEY4 == 0)
{
delay_10us(); // 延时一段时间,避免按键抖动
if (KEY1 == 0 || KEY2 == 0 || KEY3 == 0 || KEY4 == 0)
{
return 1; // 按键按下
}
}
return 0; // 按键未按下
}
// 检测按键状态,返回按下的按键值
uchar keyscan()
{
uchar keyvalue = 0xff;
while (keydown())
{
// 检测第一行按键
KEY1 = 0;
KEY2 = 1;
KEY3 = 1;
KEY4 = 1;
if (KEY1 == 0)
{
keyvalue = 0x01;
}
else if (KEY2 == 0)
{
keyvalue = 0x02;
}
else if (KEY3 == 0)
{
keyvalue = 0x03;
}
else if (KEY4 == 0)
{
keyvalue = 0x0a;
}
// 检测第二行按键
KEY1 = 1;
KEY2 = 0;
KEY3 = 1;
KEY4 = 1;
if (KEY1 == 0)
{
keyvalue = 0x04;
}
else if (KEY2 == 0)
{
keyvalue = 0x05;
}
else if (KEY3 == 0)
{
keyvalue = 0x06;
}
else if (KEY4 == 0)
{
keyvalue = 0x0b;
}
// 检测第三行按键
KEY1 = 1;
KEY2 = 1;
KEY3 = 0;
KEY4 = 1;
if (KEY1 == 0)
{
keyvalue = 0x07;
}
else if (KEY2 == 0)
{
keyvalue = 0x08;
}
else if (KEY3 == 0)
{
keyvalue = 0x09;
}
else if (KEY4 == 0)
{
keyvalue = 0x0c;
}
// 检测第四行按键
KEY1 = 1;
KEY2 = 1;
KEY3 = 1;
KEY4 = 0;
if (KEY1 == 0)
{
keyvalue = 0x00;
}
else if (KEY2 == 0)
{
keyvalue = 0x0d;
}
else if (KEY3 == 0)
{
keyvalue = 0x0e;
}
else if (KEY4 == 0)
{
keyvalue = 0x0f;
}
}
return keyvalue;
}
#endif
```
```c
// 数码管显示库函数
#ifndef __LED_H__
#define __LED_H__
#include <reg52.h>
#define uchar unsigned char
#define uint unsigned int
sbit LED8_DIO = P2 ^ 0; // 8号数码管数据线
sbit LED8_DCLK = P2 ^ 1; // 8号数码管锁存线
sbit LED7_DIO = P2 ^ 2; // 7号数码管数据线
sbit LED7_DCLK = P2 ^ 3; // 7号数码管锁存线
// 延时函数,约1ms
void delay_ms(uint ms)
{
uint i, j;
for (i = 0; i < ms; i++)
{
for (j = 0; j < 110; j++);
}
}
#endif
```
阅读全文