本项目是基于STC89C516单片机实现的一款具有浮点数运算能力的科学计算器系统。该项目是中国石油大学(北京)《硬件综合实践》课程的课程设计作品。可通过全部样例,获得100分满分。0基础的同学可以先看 入门指南.md。
提醒:本博客仅用于存档,供自己和平台上有需要的人学习使用,不可贩卖等作为他用。仅供参考,如有问题请自行解决,不负责答疑。如遇到包括但不限于没拿高分、查重被判零分等问题,后果自负,本人概不负责。
-
支持加、减、乘、除四则运算及括号嵌套
-
采用IEEE 754单精度浮点数标准,保证运算精度
-
支持最多64字节的长算式输入
-
具备语法检查功能,拦截非法表达式
-
LCD1602双行显示:
-
第一行:实时显示输入算式,支持滚动显示
-
第二行:显示计算结果或错误提示
-
-
组合式键盘:
-
4×4矩阵键盘:数字0-9、基本运算符(+, -, ×, ÷)
-
2×4独立按键:括号(, )、小数点、删除、清除、等号
-
-
除零错误检测
-
数学错误检测
-
溢出检测
-
语法错误检测(基于DFA)
-
主控制器:STC89C516单片机
-
显示模块:LCD1602液晶显示屏
-
输入模块:
-
4×4矩阵键盘(连接P1口)
-
2×4独立按键(连接P3口)
-
-
IDE:Keil uVision3
-
编程语言:C51(针对MCS-51架构的C语言)
-
编译器:μVision3 C51 Compiler
-
基于DFA的语法分析:
-
使用确定有限状态自动机进行输入校验
-
检测非法表达式格式
-
检查括号匹配
-
-
双栈表达式求值:
-
采用数字栈和运算符栈
-
处理运算符优先级
-
支持括号嵌套运算
-
-
使用
xdata关键字分配大型数据结构至外部RAM -
解决了片内RAM容量限制问题
-
支持深度嵌套运算
系统通过状态标志位管理以下状态:
-
欢迎界面状态
-
输入状态
-
计算完成状态
-
错误状态
当输入超过16个字符时,显示区域自动向左滚动,始终显示最新输入部分。
// 语法状态定义
typedef enum {
S_START, // 起始状态
S_NUM, // 数字状态
S_OP, // 运算符状态
S_LBRAC, // 左括号状态
S_RBRAC // 右括号状态
} ParserState;// 关键计算逻辑
while(opTop != -1 && peekOp() != '(' &&
getPriority(peekOp()) >= getPriority(currentOp)) {
calcTop(); // 执行栈顶运算
}通过添加微小修正值实现近似四舍五入,解决二进制浮点数表示精度问题。
| 测试表达式 | 预期结果 | 实际结果 | 状态 |
|---|---|---|---|
5.45*4-2+3 |
22.8 | 22.8 | ✅ 通过 |
3.2+4.7-2.5*2 |
2.9 | 2.9 | ✅ 通过 |
7.3+8.43+2/8 |
15.98 | 15.98 | ✅ 通过 |
3.3+7.7*2.56 |
23.012 | 23.012 | ✅ 通过 |
| 测试表达式 | 预期结果 | 实际结果 | 状态 |
|---|---|---|---|
3.45*(2.67+3.64) |
21.7695 | 21.7695 | ✅ 通过 |
19.02-3.56*(2+1) |
8.34 | 8.34 | ✅ 通过 |
5.1*(3.23+1.15-7.89) |
-17.901 | -17.901 | ✅ 通过 |
(5.56+2.78-4.6)/6.2 |
0.6032258(保留x位小数也可以) | 0.60323 | ✅ 通过 |
| 测试表达式 | 预期结果 | 实际结果 | 状态 |
|---|---|---|---|
1+2+3+4+5+6+7+8+9+10 |
55 | 55 | ✅ 通过 |
0.35*2 |
0.7 | 0.7 | ✅ 通过 |
1.0/3 |
0.3333333... | 0.33333 | ✅ 通过 |
| 测试表达式 | 预期结果 | 实际结果 | 状态 |
|---|---|---|---|
-5.3-4.1 |
-9.4 | -9.4 | ✅ 通过 |
-5*3 |
-15 | -15 | ✅ 通过 |
-2/2 |
-1 | -1 | ✅ 通过 |
-5+5 |
0 | 0 | ✅ 通过 |
| 测试表达式 | 预期结果 | 实际结果 | 状态 |
|---|---|---|---|
2/(2-2) |
错误提示 | Math Error | ✅ 通过 |
3/(5+3-8) |
错误提示 | Math Error | ✅ 通过 |
| 日期 | 主要问题 | 解决方案 |
|---|---|---|
| 2026.1.12 | LCD1602初始化后无显示 | 调节电位器V0对比度,修正初始化时序 |
| 2026.1.14 | 矩阵键盘扫描不稳定 | 增加10ms软件消抖和按键释放检测 |
| 2026.1.16 | 复杂运算结果错误,内存溢出 | 引入双栈算法,使用xdata扩展内存 |
| 2026.1.17 | 非法输入导致死机,长算式无法显示 | 实现DFA语法检查,添加滚屏显示 |
| 2026.1.19 | 浮点数显示精度问题 | 添加0.000005修正值进行四舍五入补偿 |
-
问题:计算
19.02-3.56*(2+1)时结果错误 -
解决:将栈深度从3层增加到20层,配合xdata使用
-
问题:Keil报错ADDRESS SPACE OVERFLOW
-
解决:学习8051存储架构,使用xdata利用扩展RAM
-
问题:部分十进制小数显示异常(如15.98显示为15.9799)
-
解决:理解IEEE 754标准限制,添加显示修正算法
-
问题:非法输入(如
5++6)导致系统死机 -
解决:引入DFA状态机进行输入拦截
-
功能扩展
-
添加三角函数、对数、指数等科学计算功能
-
增加存储功能(M+、M-、MR、MC)
-
-
交互优化
-
增加蜂鸣器模块提供声音反馈
-
优化键盘布局,提升用户体验
-
-
性能提升
-
优化算法效率,减少计算时间
-
增加历史记录功能
-
本项目仅用于学习交流,未经许可不得用于商业用途。
如需获取更多信息或有任何问题,请在Issues中提出。