☰
Atlas 300V 24G部署YOLO实战:从PyTorch到昇腾NPU推理全流程
2026/9/25 17:52:19 网站建设 项目流程

最近好几个人拿同一组硬件问题来问我:手头有一张Atlas 300V 24G,这玩意到底算不算运算加速卡,能不能像显卡那样直接装个PyTorch跑YOLO?老实说,我一开始也被这个问题问住了,因为在昇腾的板卡序列里,Atlas 300V这个型号经常被拿出来和GPU、和Jetson放在一起对比,但真正上手部署过的人并不算多。借着这次机会,我把之前调通YOLO部署的完整过程整理成一篇实操笔记,从硬件定位到环境搭建,再到模型转换和推理脚本,一次说清。

这篇文章适合两类人:一是刚拿到Atlas 300V 24G、正准备做目标检测项目但还没理清软件栈的工程师;二是对昇腾NPU感兴趣、想理解“模型从PyTorch到NPU上跑起来”到底要经过哪些步骤的算法同学。如果你手里没有实体卡,也可以把它当作一份项目预研参考,提前搞清楚会踩哪些坑。

1. 内容整体设计与思路拆解

1.1 Atlas 300V 24G 到底是什么硬件

先说结论:Atlas 300V 24G确实是一张运算加速卡,但它和我们熟悉的消费级GPU加速卡定位完全不一样。它是一张基于昇腾Ascend 310P处理器的PCIe推理加速卡,主打边缘侧和数据中心侧的AI推理场景,不是用来做模型训练的大算力卡。

为什么很多人会对“是不是运算加速卡”产生疑惑?因为单看外观它很像一张显卡,也是PCIe接口、有散热片、需要插到服务器主板上,但实际使用逻辑完全不同。GPU训练卡安装驱动后可以直接通过CUDA跑PyTorch,而Atlas 300V 24G需要配合华为CANN工具链,先把模型转换成昇腾专用的OM格式,再通过ACL接口调用NPU做推理。换句话说,它的“加速”能力是有明确边界的——算力集中在推理,而不是通用计算和训练。

从规格上看,Atlas 300V 24G的24GB指的是板载内存,空间足够加载YOLOv5、YOLOv8这类轻量模型,并且支持多路视频流并发推理。相比无风扇的推理卡,它带有配套散热设计,适合长时间7x24小时运行,这一点在实际项目里非常重要,因为很多视频分析场景一旦上线就是连续跑几个月,散热和功耗稳定性比瞬时峰值性能更关键。

在定位上,我习惯把它理解成一个“专门吃饭的厨师”:基本功扎实、出菜稳定,但你不能指望它去修车。YOLO这类目标检测模型正好是它的主战场,所以标题里提到的“atlas部署yolo”完全可行,只是要顺着它的一套工具链来做。

1.2 为什么选 Atlas 300V 而不是 GPU 跑 YOLO

有人会问:我手头有GPU,为什么还要用Atlas 300V?且不说供货和成本问题,单从项目需求来看,推理卡和训练卡在很多场景下根本不能互相替代。

GPU跑YOLO最好用的是推理库和生态,TensorRT、ONNX Runtime随便调,但GPU卡费高、功耗高,在机房或边缘机柜里大规模部署时不划算。Atlas 300V 24G的优势在于单卡功耗相对低,且能利用昇腾的DVPP硬件编解码模块,直接把视频流解码、缩放、抠图这些预处理搬到硬件上,释放CPU资源。对于8路、16路视频流同时跑YOLO的场景,一张Atlas 300V 24G往往就能顶住,整体性价比更好。

另一方面,选择Atlas还有一个非常实际的考量:它与昇腾其他型号(如Atlas 300I Pro、Atlas 800推理服务器)共用同一套CANN工具链和OM模型格式。也就是说,只要你在一张Atlas 300V 24G上把模型转换、推理流程整套调通,后续做大项目时,迁移到更高端的Atlas推理服务器不过是改一下soc_version和运行参数,代码层面几乎不用动。这一点对团队的技术栈延续非常有价值。

1.3 适合跑哪些 YOLO 模型

我实际跑过YOLOv5s、YOLOv8s和YOLOv5m,印象比较深的是YOLOv5s和YOLOv8s在Atlas 300V 24G上非常流畅,单帧预处理加推理加后处理整体延迟能控制在较低水平,非常适合实时视频流分析。YOLOv5m稍微吃力一点,但如果调整batch和输入尺寸,也可以满足常规需求。

不建议一上来就跑YOLOv5x或者YOLOv8x这类大模型,因为它们的主要优势在于精度,而Atlas 300V 24G的算力规格毕竟偏向边缘推理。遇到高精度场景,更好的做法是用大模型在GPU上做离线蒸馏或剪枝,再部署一个精简版到Atlas上。这只是我自己的经验,不同卡之间的算力有差异,具体选型还是要拿实际模型做一次转换测试。

2. 软硬件环境准备与工具链选型

2.1 宿主机硬件和系统要求

Atlas 300V 24G是一张PCIe卡,所以宿主机的第一要求是有一个空闲的PCIe x16插槽,并且要确保供电和散热足够。很多人忽略一个细节:这类无独立供电接口的推理卡虽然功耗不高,但周围环境温度过高时,NPU会自动降频,推理时延会明显上升。我们机房最开始把卡装在机箱最底部,旁边正好是一个硬盘位,夏天温度一上来,npu-smi里看到的芯片温度直接飙到85度,推理性能掉了三成。后来调整了风道才恢复正常。

操作系统方面,Ubuntu 20.04或22.04 x86_64是兼容性最好的选择,也可以用openEuler或CentOS,但Ubuntu的资料和踩坑案例最多,建议新手直接用Ubuntu。系统盘建议留至少50GB空间,因为CANN开发套件和依赖库加起来体积不小。内存至少要16GB,如果同时跑视频流解码,32GB会更稳。

启动前需要检查BIOS设置,确保PCIe设备没有被禁用,并且开启Above 4G Decoding。特别是部分服务器主板,默认不开启该选项会导致NPU显存分配异常。插好卡、装好系统后,使用命令lspci | grep -i ascend应该能看到设备信息,先确认硬件识别正常再继续装软件。

2.2 驱动、固件和CANN版本匹配

Atlas系列的软件安装顺序比较固定:先是NPU固件和驱动,后是CANN工具包。这里最忌讳的就是版本不匹配。华为昇腾社区提供“驱动固件与CANN版本配套表”,必须严格对照着下载,不能随手拿一个最新版就装。

以我之前用过的一个稳定组合为例:Atlas 300V 24G配Ascend HDK 23.0.RC3,CANN 6.3.RC2,系统Ubuntu 20.04,整体运行很稳。CANN每个版本都会对应不同的driver固件,装完驱动再装CANN时,要么先通过/usr/local/Ascend/ascend-toolkit/latest判断版本,要么在跑样例前用npu-smi info检查固件状态。

安装驱动的步骤看起来不复杂,但还是有一些要注意的地方。下载的驱动包是.run文件,解压后一般有一个Ascend-hdk-xxx.run,执行时建议用--full参数安装完整组件。安装完成后,重启之前最好执行一次npu-smi info,如果能看到板卡名称和芯片健康状态,说明驱动已经起来了。我遇到过驱动装好但固件版本不匹配的情况,现象是npu-smi能看到卡,但一加载模型就报驱动异常,最后重新刷固件才解决。

2.3 CANN安装与python环境配置

CANN是昇腾NPU的软件栈总称,里面既包含ATC模型转换工具,也包含pyACL、ACLLite这些运行库。我的安装经验是:以源码包方式安装toolkit比直接apt安装更容易控制版本。安装命令大致是:

chmod +x Ascend-cann-toolkit_6.3.RC2_linux-x86_64.run ./Ascend-cann-toolkit_6.3.RC2_linux-x86_64.run --install

装完后需要设置环境变量,建议把这些写入~/.bashrc,避免每次打开终端都要手动source:

source /usr/local/Ascend/ascend-toolkit/set_env.sh

Python环境建议用Python 3.8或3.9,不要一上来就追新版本到3.11,CANN里有些工具链对高版本Python兼容性还不完善。最好使用虚拟环境跑应用代码,但CANN本身安装在系统路径,所以虚拟环境里只需要安装numpy、opencv-python、pillow这些业务层依赖,基础库直接用系统CANN即可。

调试时可以用CANN安装目录下的样例工程,比如samples/contrib/ACLLite或者samples/level2_simple_inference。我的建议是先跑通一个简单的图像分类样例,确认整条工具链工作正常,再跑YOLO。别一上来就挑战最复杂的目标检测样例,不然环境问题和模型问题纠缠在一起,排查起来很痛苦。

3. 实操过程:YOLO 模型转换到昇腾 OM 格式

3.1 准备 YOLO 模型并导出 ONNX

因为CANN无法直接读PyTorch权重,我们需要先把YOLO模型导出成ONNX,再用ATC工具转换为OM。YOLOv5官方仓库自带export.py,YOLOv8可以用yolo export命令,但关键点在于导出参数设置。

首先要固定输入尺寸。我一般固定为640x640,这是个速度和精度的平衡点,也是Darknet和YOLO系列用得最多的尺寸。导出的--opset建议设为11或12,CANN对高版本opset支持有好有坏,遇到不支持的算子时先降opset,而不是先换模型。

导出时候还要注意一个细节:导出的ONNX里不要带上torch==前缀的batch维度动态,最好直接固定batch=1。对视频流部署来说,batch=1是最常见的情况,固定维度可以减少ATC转换时的优化难度。如果后续要做batch=4或batch=8,再单独导出对应batch的模型即可。

以YOLOv5s为例,导出命令大致如下:

python export.py --weights yolov5s.pt --img 640 --batch 1 --opset 11 --include onnx

这个命令会在yolov5s.onnx文件旁边生成模型。导出完成后,建议用ONNX Runtime在CPU上先跑一遍,确认输出结果是正常的,再交给ATC。很多人忽略这一步,结果模型在ONNX阶段就已经有问题,最后在NPU上报错时完全找不到原因。

3.2 ATC工具转换命令解析与实操

拿到yolov5s.onnx后,核心步骤就是用ATC把ONNX转成昇腾的.om模型。转换不是简单敲一条命令,需要理解几个关键参数。

soc_version必须和实际芯片型号对应。Atlas 300V 24G对应的昇腾芯片是Ascend 310P系列,我当时使用的是Ascend310P3。这里要特别小心,同系列下还分不同芯片小版本,写错会导致模型加载不兼容。建议通过npu-smi info或CANN文档确认具体soc_version,不要凭记忆写。

--input_shape要与ONNX里输入名和尺寸保持一致。常见YOLOv5导出后输入名为images,形状是1,3,640,640。--output指定生成的om模型名。--framework=5表示ONNX,这是固定枚举值,不用改。

基础命令是:

atc --model=yolov5s.onnx --framework=5 --output=yolov5s_bs1 --input_shape="images:1,3,640,640" \ --soc_version=Ascend310P3

这样转出来的OM模型已经能加载,但推理前还需要在应用侧做标准化、减均值、RGB通道调整等预处理。更高效的做法是利用AIPP(AI Preprocessing)模块,把图像缩放、归一化、通道变换都放到硬件里实现。AIPP配置通过--insert_op_conf指定一个.cfg文件,内容大致是:

aipp_op { aipp_mode: static input_format: RGB888_U8 src_image_size_w: 640 src_image_size_h: 640 crop: true load_start_pos_h: 0 load_start_pos_w: 0 min_chn_0: 0 min_chn_1: 0 min_chn_2: 0 var_reci_chn_0: 0.003921569 var_reci_chn_1: 0.003921569 var_reci_chn_2: 0.003921569 }

我用这个配置处理的输入是RGB顺序、0~255像素值,var_reci是1/255,所以在应用侧只需要把图片resize到640x640然后以RGB格式送入即可。如果你使用YOLOv8,注意它默认的输入格式也是RGB,不要在预处理时多做一次BGR翻转,否则颜色就会错乱,检测结果会非常诡异。

--insert_op_conf不是必须的,但强烈建议使用,因为NPU处理图像缩放和归一化的开销远小于CPU,尤其在多路视频流场景中优势很明显。

3.3 检查转换结果与OM模型可视化

转换完成后,确认yolov5s_bs1.om文件存在于当前目录,并用atc --om_info或CANN提供的模型信息工具检查输出张量信息。这里要记录一个关键信息:OM模型输出端的张量形状和名称,因为后面编写推理脚本时,我们需要从输出张量中解析类别、置信度和框坐标。

举个例子,YOLOv5的输出层一般有3个feature map,分别对应不同尺度,ONNX导出后往往是output0、output1、output2这样的名字,每个张量的形状类似[1, 255, 80, 80]、[1, 255, 40, 40]、[1, 255, 20, 20],其中255等于(5+类别数)*3,3对应每个网格的anchor数量。如果是YOLOv8,输出可能是[1, 84, 8400],84是4+80类别,8400是各尺度网格点总数。

了解这个信息非常关键,因为在后处理阶段,我们需要自己写解码和NMS逻辑,而不是直接依赖某个现成的PyTorch后处理库。刚开始接触昇腾的同学往往卡在这里:模型在NPU上跑通了,输出张量也拿到了,但不知道怎么转成最后的检测框,原因就是没搞懂输出特征的排列方式。

如果你嫌手动写解码太烦,CANN社区里也有一些开源项目实现了YOLO的OM推理和后处理,但我不建议直接照搬,最好还是自己动手读一遍输出张量,完全理解之后再去用现成代码,排查问题时会快很多。

4. 推理脚本编写与核心逻辑实现

4.1 ACL初始化与模型加载

在Python里调用NPU,我们通常会使用CANN自带的pyACL接口,或者封装更友好的ACLLite库。之前做CANN开发时,我更喜欢直接用pyACL写核心逻辑,因为ACLLite虽然简单,但一旦出问题反而难定位。

第一步是初始化ACL并设置设备:

import acl ret = acl.init() ret = acl.rt.set_device(0) context, ret = acl.rt.create_context(0)

初始化完成后,用acl.mdl.load_from_file加载OM模型。注意加载模型前,需要先为模型输入输出申请设备内存,这一步很容易被忽略。CANN的运行机制里,输入张量必须放在设备侧内存中,不能直接把numpy数组传给NPU,这和TensorRT的绑定方式有些类似。

完整推理流程可以概括为:读取图片 -> 数据预处理 -> 拷贝到设备侧内存 ->mdl.execute执行推理 -> 从输出内存取回结果 -> 后处理。写脚本时,多花一点时间把内存申请和释放封装成类,会为后面多路视频流扩展省下大量麻烦。

4.2 数据预处理细节

YOLO推理的预处理主要有三步:resize、归一化、通道调整。如果使用AIPP,那么归一化和颜色空间转换已经被NPU接管了,应用侧只需要做resize,并确保数据按NHWC或NCHW方式排布。这里有一个很容易搞混的点:AIPP配置里如果写了input_format: RGB888_U8,那么送入设备的图像数据就是RGB uint8排列,不需要再手动转成float。如果不使用AIPP,那么every pixel需要除以255并且转为FP32,通道还要按照模型要求排成CHW。

以AIPP方案为例,Python侧可以这样处理单张图片:

import cv2 import numpy as np img = cv2.imread("test.jpg") img = cv2.cvtColor(img, cv2.COLOR_BGR2RGB) img = cv2.resize(img, (640, 640)) img = img.astype(np.uint8)

注意cv2.imread默认读进来是BGR,所以要先转成RGB。如果模型训练时用的是RGB,这步就不能省。这里再强调一次:AIPP里的RGB888_U8和模型训练时的颜色顺序要保持一致,否则检测置信度会明显下降,肉眼看起来是框的位置还在,但类别全部识别错误。

resize方式也值得说一句。YOLO常用的resize是等比缩放加padding,比如原图1920x1080,先等比缩放到640x360,再在上下补黑边到640x640。简单粗暴的cv2.resize(img, (640, 640))会拉伸图像,导致检测框偏移。很多新手第一次跑YOLO出框不准,问题就出在这个预处理细节上。我在代码里封装了一个letterbox函数,逻辑很简单:计算缩放比例,填充两边,最终输出640x640。

4.3 执行推理与数据拷贝

数据准备好后,需要将numpy数组通过acl.rt.memcpy拷贝到设备内存。这里镇上的坑是数据对齐。昇腾的设备内存一般要求16字节对齐,虽然部分CANN版本内部会做处理,但最稳妥的方式是使用acl.util.np_to_ptr或np.ctypeslib转成指针时,确保原始numpy数组是连续内存。

模型的输入和输出尺寸无法事先完全确定,建议在加载模型后,调用acl.mdl.get_input_size_by_index和acl.mdl.get_output_size_by_index获取实际字节数,再申请对应大小的设备内存。以前我图省事直接按经验值开了个大buffer,结果是把输出张量切错了,导致后处理时变量错位,查了半天才发现是buffer大小没对齐。

推理执行使用acl.mdl.execute,它是一个同步或异步接口。如果是视频流场景,建议使用acl.mdl.execute_async加stream,或者直接把推理放到独立线程里,避免阻塞主循环。单张图片调试时用同步版本就够了。

执行完成后,用acl.rt.memcpy把输出数据从设备侧拷贝回主机侧numpy数组,然后释放内存。这个流程在实际工程里会循环几千上万次,所以内存复用非常重要,尽量在初始化时一次性申请好输入输出buffer,不要在每次循环里反复申请释放,否则GC会拖慢整个推理速度。

4.4 输出解析与后处理

拿到输出张量后,需要自己实现解码。以YOLOv5为例,三个输出的形状为[1, 255, 80, 80]、[1, 255, 40, 40]和[1, 255, 20, 20]。我先将每个张量从CHW转成HWC,然后按anchor进行解码,得到框坐标、置信度和类别概率。

具体解码公式在YOLOv5源码里写得很清楚:中心点坐标通过sigmoid激活后加上网格偏移,再乘以对应的stride(分别是8、16、32),宽和高用anchor固定的宽高乘以指数的预测值再乘以stride。解码之后,所有检测框都映射到640x640坐标系中,此时如果原图不是640x640,还需要根据之前letterbox的缩放比例和padding偏移,将坐标还原回原图尺寸。

YOLOv8的输出解码稍有不同,它的框中心坐标和宽高是直接回归得到的,不需要anchor解码,但需要做一次sigmoid和坐标缩放。无论哪个版本,最后的NMS(非极大值抑制)都可以在CPU上用numpy实现,也可以使用opencv的dnn.NMSBoxes。NMS放在CPU上做对整体性能影响不大,因为候选框数量有限。

为了调试方便,第一次写后处理时可以在代码里把解码后的检测结果直接画到原图上,再和官方PyTorch推理结果对比。如果框的位置和类别一致,说明解码逻辑正确;如果不一致,大概率是颜色顺序、归一化或缩放偏移其中一项出了问题。

5. 常见问题与排查技巧实录

5.1 问题速查表

现象可能原因解决办法
npu-smi info看不到设备驱动未装好或板卡未识别检查PCIe插槽和BIOS,确认Above 4G Decoding开启
加载OM模型报错soc_version或CANN版本不匹配确认芯片型号,对照官网驱动和CANN配套表
转换ATC时报Unsupported OpONNX opset过高或算子不受支持降低opset,或者查看日志定位具体算子并替换
推理结果全为零AIPP配置或输入数据格式错误检查颜色通道、输入尺寸、是否使用letterbox
检测框位置偏差很大resize方式错误或还原坐标时参数错使用letterbox等比缩放,记录缩放比例和偏移量
多路视频流CPU占用过高预处理或后处理放在Python循环里执行使用DVPP硬件解码和多线程,避免每帧重复申请内存
推理时延偶尔跳动很大NPU降频或内存碎片检查芯片温度,优化内存复用,关闭后台频繁的python任务

这张表是我在实际项目中根据问题记录逐渐总结出来的,比较简略,但覆盖了大部分新手会碰到的点。

5.2 模型输出全是背景框的排查过程

有一次我转换YOLOv8s后,推理结果的置信度全部在0.1以下,几乎没有有效检测框。当时我没有怀疑模型转换,因为ATC转换过程没有任何报错,但跑出来的结果就是不对。

逐层排查后发现两个问题:第一,YOLOv8的ONNX输出张量是解码前的原始输出,但我在后处理里直接用sigmoid处理了所有值,导致坐标分布被压到0~1之间;第二,输入图片在letterbox之后没有去掉填充部分,坐标还原时偏移计算错误。修改解码逻辑后,检测框就正常了。

这件事给我一个教训:不同YOLO版本的后处理差异很大,不能拿YOLOv5的代码直接去套YOLOv8,而且调试时要先固定一个输入,在NPU推理前打印预处理后的图像,在推理后打印原始输出张量,一步步对比,比盲目改代码高效得多。

5.3 固件与驱动版本不匹配的现场处理

Atlas系列最容易踩的坑之一,就是驱动和固件版本不匹配。我之前有一次为了尝试新特性,把CANN从6.3.RC2升级到了6.3.RC3,但没有同步升级固件。升级后NPU能正常初始化,可推理时每次都报device error。

当时系统日志里并没有明显错误,我一度怀疑是板卡硬件故障。后来冷静下来查配套表,才发现新CANN对应新固件,旧固件不能兼容。解决方案是在固件包解压目录里执行:

./Ascend-hdk-xxx.run --upgrade

升级完重启,问题立即消失。以后每次升级CANN之前,我都会先去官网确认对应的HDK固件版本,再决定是否一起升级。这类问题虽然技术上不复杂,但排查过程非常耗时,提前避坑能省下大半天。

5.4 多路视频流性能优化心得

单张图片推理跑通后,项目通常就会要求“能不能跑8路视频流”。我建议不要一上来就开8个线程暴力推理,先用两路视频流做基准测试,观察NPU利用率、CPU占用和内存占用,再逐步增加路数。

Atlas 300V 24G的NV12/DVPP硬件解码能力很重要。如果直接用OpenCV读取RTSP流并用CPU解码,8路1080p视频能把CPU拖到100%,NPU反而在空等数据。正确做法是用昇腾的DVPP模块做视频解码,再把一帧帧图像直接送到NPU预处理和推理,CPU只负责读码流和后期业务逻辑。

我在实际项目中还发现,多路视频流共享同一个OM模型时,不要每路单独加载一次模型,应该只加载一次,再把多路输入数据拷贝到不同的输入buffer里,通过batch或复用同一个模型对象依次推理。这样可以显著降低设备内存占用。内存充足时也可以考虑batch方式,一次推理多帧,吞吐量提升明显,但会增加单帧时延,要根据场景取舍。

6. 部署完成后的检查清单与扩展建议

6.1 部署后的基本检查项

检查项操作判断标准
模型加载npu-smi info,应用日志无报错板卡识别正常,模型加载后内存占用稳定
单帧时延对同一张测试图连续推理100次平均时延波动小于10%,无明显尖峰
长时间稳定性连续运行24小时,观察内存和温度NPU温度不超过85度,无内存泄漏
多路并发逐渐增加视频路数到目标值CPU占用不持续增长,NPU利用率合理
检测精度用标准测试集对比原始PyTorch结果mAP指标下降在可接受范围内

做完这五项检查,基本可以认为YOLO部署已经合格。

6.2 从转接到上线的常用扩展方向

如果只是把Demo跑通,其实只完成了第一步。后续上线前,通常还建议做模型量化。昇腾CANN支持将FP16或INT8的OM模型用于推理,尤其INT8在Atlas 300V 24G这类边缘卡上能明显提升吞吐量。但量化会带来精度损失,需要通过校准数据集验证精度,不能盲目开启。

另外可以考虑使用MindSpore或者昇腾提供的模型迁移工具,把训练端也搬到昇腾生态里。不过从投入产出比上看,大多数团队继续用PyTorch训练模型,只把推理端迁移到Atlas是更务实的方案。CANN提供充足的ONNX支持,暂时不碰训练端也能完成落地。

再往外扩展,可以接入昇腾的MindX SDK、ModelBox等推理框架,它们自带了一些视频流处理、模型管理和调度能力,适合做相对完整的服务化部署。不过这些框架的好处建立在工程复杂度之上,小项目直接用pyACL脚本自研一个简易推理服务反而更清晰。

6.3 一点个人经验

从第一次在Atlas板上跑通YOLO到现在,我最大的感受是:昇腾工具链的文档和报错信息确实不如NVIDIA生态那么友好,但一旦理解了它的设计思路——模型转换必须标准化、数据预处理尽量下沉到硬件、后处理要在CPU侧处理好边界,后面再做类似项目会越来越顺手。

如果你是第一次接触这款卡,不要急着并行搞太多任务,先把一条最基础的“ONNX转OM、单图推理、后处理画框”流水线跑顺。这个过程中遇到的问题基本能覆盖后续开发里八成以上的坑。等这条线稳定了,再考虑多路视频流、INT8量化、模型服务化这些进阶内容。

另外,我在实际部署中还有一个习惯:把ATC转换命令和后处理的关键参数做成配置文件保存下来,每次换硬件型号或模型版本时,只用修改几个参数,不用重新翻文档。这个习惯帮我节省了大量时间,也推荐给你试试。

需要专业的网站建设服务?

联系我们获取免费的网站建设咨询和方案报价,让我们帮助您实现业务目标

立即咨询