Front-End and Back-End Separated Calculator System
Software Engineering Practice Assignment 1 - Front-End and Back-End Separated Calculator System
## 课程信息
| 项目 | 内容 |
| 计算器 | --- |
| 这个作业属于哪个课程 | 软件工程实践 |
| 作业要求 | 前后端分离计算器系统 |
| 这个作业的目标 | 理解前后端分离、HTTP API、表达式解析、数据库持久化和软件工程基本流程 |
| 学号 | 832401308 |
| 姓名 | 黄和 |
| 其他参考文献 | PEP 8、Google JavaScript Style Guide、FastAPI 文档 |
## 目录
1. [Git 仓库和代码规范链接]
2. [PSP 表格]
3. [成品展示]
4. [设计与实现过程]
5. [代码说明]
6. [部署与测试]
7. [心路历程与收获]
## 一、Git 仓库和代码规范链接
- 前端 GitHub 仓库:https://github.com/Huang269999/832401308_calculator_frontend

- 后端 GitHub 仓库:https://github.com/Huang269999/832401308_calculator_backend
- 前端代码规范:https://github.com/Huang269999/832401308_calculator_frontend/blob/main/codestyle.md
- 后端代码规范:https://github.com/Huang269999/832401308_calculator_backend/blob/main/codestyle.md
- 公网访问地址:https://huang269999.github.io/832401308_calculator_frontend/
## 二、PSP 表格
> 下表中的“预计时间”可以作为开发前记录的参考;“实际时间”必须按你自己的真实开发过程填写。
| PSP 阶段 | 预计时间(分钟) | 实际时间(分钟) |
| 需求分析 | 20 | 60 |
| 系统设计 | 25 | 90 |
| 前端开发 | 90 | 180 |
| 后端开发 | 90 | 180 |
| 表达式计算模块 | 45 | 60 |
| 数据库设计 | 30 | 30 |
| 历史记录模块 | 35 | 30 |
| 前后端联调 | 45 | 45 |
| 测试与修复 | 50 | 15 |
| 部署 | 40 | 120 |
| 博客整理 | 60 | 60 |
| **合计** | **530** | **870** |
## 三、成品展示
本项目实现了一个前后端分离的 Web 计算器。前端负责用户交互与结果展示,后端负责表达式解析、计算、异常处理以及 SQLite 数据持久化。


###3.1 主界面

### 3.2 加法
输入 `12+8`,后端返回结果 `20`。

### 3.3 减法
输入 `5-8`,结果为 `-3`。

### 3.4 乘法和除法
分别测试 `3*7` 和 `10/2`。

### 3.5 小数与复合表达式
测试 `1.5+2.8`、`1+2*3`,验证小数和运算符优先级。

### 3.6 括号与一元负号
测试 `(1+2)*3`、`-5+8`。


### 3.7 异常处理
测试 `1/0` 与非法表达式 `1+++`,后端返回错误信息,前端进行展示。


### 3.8 历史记录与删除
成功计算会写入 SQLite。刷新前端页面后记录仍然存在;点击某一条记录的“删除”按钮后,前端调用后端删除接口并重新拉取数据库数据。

### 3.9 扩展功能
项目额外实现:
- 清空全部历史记录;

- 键盘 Enter 计算、Esc 清空;

- 明暗主题切换。

- 后端在线状态显示。

## 四、设计与实现过程
### 4.1 需求分析
核心需求包括四则运算、复合表达式、括号、小数、一元正负号、非法表达式和除零处理;每次成功计算必须保存到后端数据库;前端必须能够读取历史并删除指定记录。
本次作业的关键不是单纯实现一个计算器,而是保证“最终计算结果由后端生成”。因此前端只发送表达式,不负责表达式求值。
### 4.2 总体架构
```text
浏览器前端
HTML + CSS + JavaScript
|
| HTTP / JSON
v
FastAPI 后端
|
|-- 表达式校验
|-- AST 安全解析
|-- 数学计算
|-- 异常处理
v
SQLite 数据库
calculation_history
```
### 4.3 功能结构图
```text
Calculator System
|
|-- Calculator
| |-- Basic Calculation
| |-- Compound Expression
| |-- Error Handling
|
|-- Calculation History
| |-- Save History
| |-- Query History
| |-- Delete History
| |-- Clear History (扩展)
|
|-- Front End
| |-- User Input
| |-- Result Display
| |-- History Display
| |-- Theme Switch (扩展)
|
|-- Back End
|-- API
|-- Safe Expression Parser
|-- Calculation Service
|-- SQLite Database
```
### 4.4 前端设计
前端使用原生 HTML、CSS 和 JavaScript。这样可以减少框架依赖,并把重点放在前后端交互上。
前端职责:
1. 收集用户表达式;
2. 调用 `POST /api/calculate`;
3. 显示后端返回的结果或错误;
4. 调用 `GET /api/history` 显示数据库历史;
5. 调用 `DELETE /api/history/{id}` 删除指定记录。
前端没有表达式计算逻辑。如果停止后端,用户仍可输入和点击按键,但无法得到新的有效结果。
### 4.5 后端设计
后端采用 FastAPI,将计算逻辑、数据访问和 API 分开:
- `calculator_service.py`:安全解析和计算;
- `database.py`:SQLite CRUD;
- `schemas.py`:请求数据校验;
- `main.py`:HTTP API。
### 4.6 API 设计
| 方法 | 地址 | 说明 |
| --- | --- | --- |
| POST | `/api/calculate` | 计算表达式并保存历史 |
| GET | `/api/history` | 查询历史记录 |
| DELETE | `/api/history/{id}` | 删除指定历史 |
| DELETE | `/api/history` | 清空全部历史(扩展) |
| GET | `/api/health` | 后端健康检查(扩展) |
计算请求:
```json
{
"expression": "(1+2)*3"
}
```
计算成功:
```json
{
"success": true,
"id": 1,
"expression": "(1+2)*3",
"result": 9
}
```
### 4.7 数据库设计
```text
calculation_history
-------------------
id INTEGER PRIMARY KEY AUTOINCREMENT
expression TEXT NOT NULL
result TEXT NOT NULL
created_at TEXT NOT NULL
```
SQLite 文件由后端首次启动时自动创建。前端刷新或重新打开不会清除数据库数据。
### 4.8 计算模块设计
为了避免直接执行用户输入,本项目没有使用 `eval()` 或 `exec()`。
实现步骤:
1. 将界面中的 `×`、`÷` 标准化为 `*`、`/`;
2. 使用 Python `ast.parse(..., mode="eval")` 将表达式解析为语法树;
3. 只允许数字常量、`+ - * /`、括号形成的语法结构、一元 `+ -`;
4. 遇到函数调用、变量、列表、幂运算等其他节点立即拒绝;
5. 递归计算允许的 AST 节点;
6. 对除数为 0、表达式过长和结果过大等情况进行异常处理。
这种方式利用 AST 完成“解析”,但没有把表达式作为普通 Python 程序直接执行。
### 4.9 前后端交互流程
```text
用户输入表达式
↓
前端 POST /api/calculate
↓
后端校验并解析表达式
↓
后端完成数学计算
↓
成功结果写入 SQLite
↓
后端返回 JSON
↓
前端显示结果
↓
重新查询并显示历史记录
```
## 五、代码说明
### 5.1 前端 API 请求
前端使用 `fetch()` 把表达式作为 JSON 发送给后端。收到响应后直接显示 `data.result`,前端自身不计算表达式。
### 5.2 安全表达式解析
后端通过 AST 对允许的节点做白名单判断,只接受四则运算和一元正负号。任何函数调用、属性访问或其他 Python 语法都会被拒绝。
### 5.3 数据库插入
只有成功计算后才调用 `save_history()`,因此非法表达式与除零错误不会产生历史记录。
### 5.4 历史查询与删除
前端通过 `GET /api/history` 读取数据库记录;删除时将记录 ID 发给后端,后端执行 SQL `DELETE`,随后前端重新读取历史列表。
## 六、部署与测试
### 6.1 本地后端
```bash
pip install -r requirements.txt
uvicorn app.main:app --reload
```
### 6.2 本地前端
```bash
python -m http.server 5500 -d src
```
### 6.3 公网部署
- 前端地址:https://huang269999.github.io/832401308_calculator_frontend/
- 后端地址:https://832401308calculatorbackend-production.up.railway.app/docs
部署后应将前端 `src/config.js` 的 `API_BASE_URL` 改为公网后端 HTTPS 地址,并在后端设置 `CORS_ORIGINS` 为公网前端域名。
### 6.4 测试用例
| 输入 | 预期结果 |
| --- | --- |
| `1+2` | `3` |
| `5-8` | `-3` |
| `3*7` | `21` |
| `10/2` | `5` |
| `1.5+2.8` | `4.3` |
| `1+2*3` | `7` |
| `(1+2)*3` | `9` |
| `-5+8` | `3` |
| `3*-2` | `-6` |
| `1/0` | 返回除零错误 |
| `1+++` | 返回表达式格式错误 |
## 七、心路历程与收获
本次作业让我第一次比较完整地理解了前后端分离项目的基本流程。最开始容易把“网页计算器”理解成在 JavaScript 中直接计算,但作业要求强调最终结果必须由后端生成,因此我重新梳理了前后端职责:前端负责交互,后端才是业务逻辑和数据的真实来源。
实现过程中比较关键的问题是表达式解析。如果直接使用 `eval()` 虽然代码很短,但存在任意代码执行风险,也不符合题目要求。因此最终使用 AST 解析表达式,并只允许指定的数学节点。这样既保留了运算符优先级和括号等语法能力,也能够拒绝函数调用等危险输入。
第二个明显收获是数据库持久化。只有把历史记录真正写入 SQLite,前端刷新以后数据才不会消失,这让我更直观地区分了浏览器临时状态和后端持久数据。
通过本次实践,我进一步熟悉了 HTTP API、JSON、CORS、SQLite、异常处理、Git 仓库拆分以及前后端联调的完整流程。后续还可以继续增加科学计算、搜索分页、用户登录等功能。
相关推荐
嵌入式Linux驱动开发实战(四):温湿度IMU传感器驱动+应用层采集完整工程-从内核到用户空间的全链路实战
本文以温湿度传感器(HTU21D/SHT30)和IMU传感器(MPU9250/ICM20948)为例,完整呈现从设备树配置、I2C/SPI驱动编写、hwmon/IIO子系统集成,到用户空间采集应用开发的全链路工程实践。
【二维快速傅里叶变换的调频连续波雷达目标参数估计】基于FMCW雷达体制的距离多普勒联合估计与恒虚警检测方法研究(Matlab代码实现)
内容概要:本文系统解读了一套完整的多机器人路径规划(MAPF)MATLAB代码库,聚焦于优先级规划算法的工程实现。该框架采用“几何—拓扑—调度—呈现”四层解耦架构,涵盖地图解析、四邻域拓扑与Petri网建模、基于优先级启发式的路径规划、时间同步与冲突消解等核心模块,并提供动画与视频可视化支持。其核心设计思想为“空间规划与时间消解分离”,通过动态边权膨胀引导避让、节点预留历史优化冲突查询、几何惩罚驱动的局部同步等机制显著提升算法效率与可扩展性。文章还对比分析了三种同步策略的适用场景,探讨了Petri网双阶段优化路径,并对框架的完备性、复杂度及工程可维护性进行了系统评价,旨在为MAPF的研究与教学提供一份可复现、可批判的参考范本。; 适合人群:具备一定算法基础和MATLAB编程经验,从事路径规划、机器人调度、智能交通等相关领域研究的科研人员及研究生。; 使用场景及目标:① 学习多机器人路径规划的基本流程与关键技术实现;② 掌握优先级规划、冲突消解、Petri网建模等核心算法的设计与优化方法;③ 借鉴模块化、分层解耦的工程框架设计思路,用于仓储物流、无人机编队等实际场景的算法开发与仿真验证。; 阅读建议:建议结合文中提到的MovingAI地图数据与MATLAB环境运行代码,逐步调试各模块以深入理解算法细节,并重点关注动态边权膨胀与局部同步策略的实现逻辑,以便在实际应用中进行参数调优与功能扩展。
YOLO算法隧道内车辆目标检测数据集-52张-包含 VOC 和 Yolo 格式标签-支持多种算法训练模型.zip
页面底部附数据集可视化效果预览,可直接参考。 YOLO隧道内车辆目标检测数据集 目标类别:['bus', 'car', 'motocycle', 'truck'] 中文类别:['公交车', '轿车', '摩托车', '卡车'] 训练集:41 张 验证集:11 张 测试集:0 张 总计:52 张 该数据集提供了data.yaml文件,内容如下: train: ../train/images val: ../valid/images test: ../test/images nc: 4 names: ['bus', 'car', 'motocycle', 'truck'] 使用场景:毕业设计、课程设计、深度学习入门、工业场景落地验证。
loras.7z.007
loras.7z.007
(共159页PPT)麦肯锡图表汇总.ppt
(共159页PPT)麦肯锡图表汇总.ppt


