# Minist **Repository Path**: BUAA-CI-LAB/minist ## Basic Information - **Project Name**: Minist - **Description**: No description available - **Primary Language**: Unknown - **License**: Not specified - **Default Branch**: lab - **Homepage**: None - **GVP Project**: No ## Statistics - **Stars**: 0 - **Forks**: 0 - **Created**: 2026-09-11 - **Last Updated**: 2026-09-11 ## Categories & Tags **Categories**: Uncategorized **Tags**: None ## README # Lab1 深度神经网络 北京航空航天大学计算机学院 ## 1 实验目标 搭建深度神经网络,并在给定数据集上进行训练与测试。具体要求: - 使用深度学习框架 PyTorch 完成网络搭建 - 使用 Python 语言,版本 >= 3.13,项目使用 [uv](https://docs.astral.sh/uv/) 管理 Python 环境与依赖 - 数据集可以使用提供的 MNIST 数据集,也可自行调用神经网络框架相应接口下载并加载 MNIST 数据集 - 可使用提供的模板项目,在其基础上进行修改完善,也可以重新编写代码。模板提供了框架,包括数据 IO 与模型训练以及测试,同学们的主要任务为模型定义与参数调整 ## 2 环境配置 本项目使用 uv 管理 Python 环境,克隆项目后执行以下命令即可完成环境配置: ```bash uv sync ``` uv 会根据 `pyproject.toml` 与 `uv.lock` 自动创建虚拟环境并安装依赖,主要依赖包括: - torch:深度学习框架(CUDA 13.0 构建,无 NVIDIA GPU 的机器会自动使用 CPU 运行) - numpy:数据处理 - tensorboard:训练过程可视化 运行代码时统一使用 `uv run` 命令,例如 `uv run pt_mnist.py`,无需手动激活虚拟环境。 ## 3 数据集获取与使用 本次实验采用 MNIST 官方数据集[^1],模板项目的 `mnist_data` 目录下亦有相关文件。数据集划分如下: - 训练集 train:55000 张 - 验证集 validation:5000 张 - 测试集 test:10000 张 每张图片尺寸为 28 × 28,标签为 0-9 共 10 个数字。若本地文件缺失,程序会自动从 MNIST 官网下载。 [^1]: http://yann.lecun.com/exdb/mnist/ ## 4 代码介绍 ### 4.1 代码结构 模板项目基于 PyTorch 编写,代码结构如下: - `input_data.py`:读取数据集文件,用于加载 MNIST 数据集 - `pt_mnist.py`:主文件,包含训练、测试流程以及模型保存的实现 - `data_object.py`:数据类文件,包含数据处理的实现 - `pt_network.py`:网络结构文件,包含网络结构实现(**需要同学们完成的部分**) - `pt_test_model.py`:加载保存的模型并测试准确率 - `main.py`:程序入口,直接运行训练与测试流程 ### 4.2 网络结构 LeNet 模型结构如下图所示,网络由 2 层卷积层、2 层池化层、2 层全连接层组成。可以发现,该网络输入(32 × 32)与 MNIST 数据集(28 × 28)不匹配,同学们可以采用两种解决方式:1)对输入图片周围补零(Padding 操作)至网络输入大小;2)修改第一层卷积层,使其输出与图中 C1 大小一致。更多网络细节可参考链接[^2]。 ![LeNet 模型结构图](docs/lenet.png) LeNet 模型结构定义在 `pt_network.py` 文件中,其中需要自行补充的代码为 `LeNet` 类中的 `__init__` 函数与 `net` 函数。 `__init__` 函数用于定义网络各层,可以使用 PyTorch 提供的 `nn.Conv2d`(卷积层)、`nn.MaxPool2d`(池化层)、`nn.Linear`(全连接层)等模块: ```python def __init__(self): """ Define network layers. You can use nn.Conv2d / nn.MaxPool2d / nn.Linear to define layers, for example: self.conv1 = nn.Conv2d(in_channels=1, out_channels=6, kernel_size=5) self.pool1 = nn.MaxPool2d(kernel_size=2, stride=2) self.fc1 = nn.Linear(in_features=256, out_features=120) """ super().__init__() # layer 1 # TODO: construct the conv1 ... ``` `net` 函数被 `forward` 前传函数调用,包括了网络结构定义和前向传播两个过程,函数中包含 `feats` 参数,代表输入的图像数据,返回值则为前向传播后输出的 logits 结果: ```python def net(self, feats): """ Define network forward process. :param feats: input features, shape (batch_size, 1, 28, 28) :return: logits, shape (batch_size, 10) """ # layer 1 # TODO: use conv1 and activation function ... ``` [^2]: https://www.cnblogs.com/wuliytTaotao/p/9544625.html ### 4.3 代码流程 LeNet 模型训练与测试流程在 `pt_mnist.py` 文件中,主要用于对 LeNet 模型进行初始化、模型训练以及测试。 在主函数中,程序创建了 `LeNet` 实例、损失函数(`nn.CrossEntropyLoss`)与优化器(`torch.optim.Adam`),调用 `train_net` 函数进行模型训练,`test_net` 函数进行模型测试。在 `train_net` 函数中,训练完成的模型保存路径为 `model/model.pt`: ```python # start training train_net(data.train, data.validation) print("Training time: {:.3f}s.\n".format(time.time() - start_training_time)) ... acc = test_net(data.test) print("Test Accuracy = {:.5f}".format(acc)) print("Testing time: {:.5f}s\n".format(time.time() - start_testing_time)) ``` 而在 `pt_test_model.py` 文件中,使用者可以载入已保存的模型进行模型测试,评估模型的性能: ```python # create instance of neural network and load saved parameters net = LeNet().to(device) net.load_state_dict(torch.load('./model/model.pt', weights_only=True)) ... # get accuracy and loss test_accuracy, loss = test_model(data.test) print("Test Loss = {:.5f}, Validation Accuracy = {:.5f}\n".format(loss, test_accuracy)) ``` ## 5 作业要求 实现 `pt_network.py` 中的 `LeNet` 类,使 `pt_mnist.py` 能够正常运行。网络要求结构如下所示: - 网络输入:`(batch_size, 1, 28, 28)` 的张量,其中 `batch_size` 为每批次中包含图片的数量,这个数值可以根据自己硬件条件进行确定;28 × 28 为给定的图片尺寸 - 网络输出:10 个输出节点,分别代表 0-9 这 10 个数字。本次作业不对精度做特别的要求,只需在合理范围内(> 80%)即可 - 网络模型:建议采用 LeNet,也可以采用其他自己定义的网络模型(可适当调整网络以适配数据集输入维度大小),调参并对比效果 ## 6 作业提交 - 若程序正常运行,则模型的结构与参数将会保存至 `model/model.pt` 中,无需进行额外操作 - 撰写实验报告,包括但不限于网络原理说明、网络实现代码介绍、训练过程截图、测试精度结果截图等。**建议采用 Markdown 格式撰写报告,最终导出 PDF 提交**。报告命名格式:学号 + 姓名 + 作业一报告.docx(.pdf),如 XXXXXXXX + 张三 + 作业一报告.docx(.pdf)(实验报告的撰写格式要求与建议请参考 [实验报告撰写格式](docs/实验报告撰写格式.md)) - 将完整的工程文件夹(**需要包含模型 model 文件夹,不需要数据文件夹 mnist_data**)、实验报告打包成压缩文件。压缩文件命名格式:学号 + 姓名,如 XXXXXXXX + 张三 + 作业一.zip(.rar) ## 7 其他 ### 7.1 模型训练说明 本次作业使用的 MNIST 数据集中包含训练集 60000 张图片,如果在 CPU 上训练时间过长,可以考虑采用 GPU,或者减少训练集的大小(但会降低训练后的模型精度)。程序会自动检测并使用可用的 GPU(CUDA),无需额外配置。 模板中默认的超参数如下,同学们可以自行调整并观察对训练效果的影响: - 学习率 lr = 0.001 - 批次大小 batch_size = 1000 - 训练轮数 epochs = 10 ### 7.2 TensorBoard 数据可视化 TensorBoard 提供机器学习实验所需的可视化功能和工具,建议学习和使用该工具[^3]: 模板代码中已经写入了 TensorBoard 相关语句,程序运行结束后工程目录下将会生成 `logs` 文件夹,接下来执行以下两步打开 TensorBoard: - 在终端中输入:`uv run tensorboard --logdir=./logs` - WSL 中由于网络配置问题可能导致tensorboard服务无法正常启动,可以做如下的临时修复: ```python # 在 .venv/lib/python3.13/site-packages/tensorboard/program.py # 找到函数 def is_port_in_use(port): with socket.socket(socket.AF_INET, socket.SOCK_STREAM) as s: return s.connect_ex(("localhost", port)) == 0 # 修改为 def is_port_in_use(port): with socket.socket(socket.AF_INET, socket.SOCK_STREAM) as s: s.settimeout(0.1) return s.connect_ex(("localhost", port)) == 0 ``` - 按照提示在浏览器中输入获得的网址(默认为 http://localhost:6006 )打开 TensorBoard 打开后即可清晰地观察训练过程 loss 以及 accuracy 变化曲线。 [^3]: https://www.tensorflow.org/tensorboard/get_started