☰
树莓派5部署YOLOv5的边缘视觉检测实战:从开发板到车间
2026/10/31 1:11:32 网站建设 项目流程

把树莓派 5 从调试桌挪进车间,这件事我原以为三天能搞定,结果卡了快两周。背景是产线上有一个外观检测工位,之前靠人工盯,我想用自己训练的 YOLOv5 模型做替代,挑了几种边缘设备,最后选了树莓派 5 跑 Ubuntu 的方案。这么选不是因为它在同类板子里算力最猛,而是 arm64 生态成熟,Python 侧的工具链基本无缝移植,坏了一台能快速换新,成本也在车间审批范围内。

这里先放结论:如果只把树莓派 5 当开发板玩,那很简单;但要放在车间里连续运行,真正卡住你的往往不是 YOLOv5 本身,而是系统安装、模型部署、供电、散热、网络、掉电恢复这六件事。下面逐条拆开讲,每条都是实际踩过的坑,适合准备把树莓派 5 用于边缘视觉检测、又没太多工业部署经验的朋友参考。

1. 装系统这事,比预想中讲究

1.1 为什么最终选择了 Ubuntu

我一开始用的是树莓派官方系统 Raspberry Pi OS,它确实开箱即用,桌面环境也顺手,但真拿到产线边上跑了两天就发现几个问题:首先是软件源里很多 arm64 包版本偏旧,装新版 PyTorch 时依赖容易冲突;其次是公司内部要对接的视觉 SDK 和主控程序都在 Ubuntu LTS 环境下测试过,换到官方系统等于给自己增加适配成本。

所以最终选了 Ubuntu Server 24.04 LTS,而不是桌面版。车间设备不需要显示器,桌面环境白白占掉内存,还会时不时弹出提示干扰无人值守运行。安装时直接烧 Ubuntu Server 镜像,系统装完默认无桌面,内存占用小,SSH 上去操作也干净。

这里也给个建议:树莓派 5 建议买 8GB 内存版。虽然跑 YOLOv5s 时 4GB 也能跑,但一旦同时开摄像头采集、ONNX Runtime 推理、日志记录和网页状态面板,内存直接吃紧。8GB 能让你少处理很多 swap 调优的麻烦。

1.2 烧录与初始化流程

树莓派 5 的安装方式比前几代更成熟,直接用 Raspberry Pi Imager 就能完成。关键操作是选镜像时要下载官方维护的 Ubuntu Server 24.04 树莓派版,烧录目标选一张 A2 速度等级的 microSD 卡,容量建议 32GB 起步,别用杂牌卡,后面跑模型写入非常多,垃圾卡很容易在装依赖时直接让系统卡死。

烧录前可以在 Imager 的高级设置里预置 SSH、用户名和密码,免去插显示器键盘的麻烦。第一次开机后先做三件事:更新固件、换软件源、开静态 IP。树莓派 5 的 EEPROM 固件会持续修复 USB 启动和电源管理方面的问题,所以先执行sudo rpi-eeprom-update -a把固件更新到最新。这一步在长时间运行场景里非常重要,旧固件在意外断电后偶尔会丢外设。

软件源方面,如果在车间内网有管理员维护的 apt 镜像,直接换成内网地址;没有就按 Ubuntu 官方源先用着,重点是装完依赖后记得做一次sudo apt update && sudo apt upgrade,把内核和驱动拉到同一版本,避免后续排查问题时分不清是系统bug还是硬件故障。

1.3 开机后别急着跑模型

系统刚装好时,我犯过一个低级错误:直接 clone YOLOv5 仓库开跑,结果报了一堆缺库错误。后来老实按顺序装系统工具:python3-pip、python3-venv、git、cmake、build-essential、libopenblas-dev,再建一个虚拟环境单独装 Python 依赖。用虚拟环境不是因为洁癖,而是车间设备如果装乱了系统 Python,恢复起来代价极高。

另外一个容易忽略的是时区设置。树莓派 5 默认时区是 UTC,日志时间和车间监控平台对不上,排查问题时时间轴全乱了。执行sudo timedatectl set-timezone Asia/Shanghai后,再把日志时间格式统一,之后所有排障都顺畅很多。

2. 自己训练的 YOLOv5 模型,怎么在树莓派5上跑起来

2.1 环境搭建:Python、PyTorch 与 aarch64

Ubuntu 24.04 自带的 Python 版本偏高,但树莓派是 aarch64 架构,不能直接用 x86 桌面上那套习惯来装包。PyTorch 官方为 aarch64 提供了 CPU 版本,直接用 pip 装就行:

python3 -m venv ~/yolo_env source ~/yolo_env/bin/activate pip install torch torchvision --index-url https://download.pytorch.org/whl/cpu

装完后务必确认 torch 能正常导入,并且torch.backends.mkldnn可用。很多人直接装 ultralytics 全家桶,我实际用下来觉得太重,如果你的推理程序已经写好,只依赖原版 YOLOv5 的导出逻辑,那么运行时可以只保留 onnxruntime,不必在树莓派上再维护一套训练框架。

OpenCV 建议装opencv-python-headless,而不是带 GUI 的版本。因为车间环境没有显示器,带 GUI 版本会增加一堆 X11 依赖,而且偶尔会因为缺 libGL 直接崩掉。headless 版本只提供图像处理能力,干净利落。

2.2 模型导出与量化

自己的训练产物一般是.pt权重文件,直接在树莓派上用 PyTorch 推理速度太慢,我建议先导出成 ONNX,再用 ONNX Runtime 跑。导出操作在训练机上完成,PyTorch 的版本只要和训练时一致就不会出问题:

yolo export model=best.pt format=onnx imgsz=640 dynamic=False

dynamic=False很关键。动态输入维度在 CPU 推理时会带来额外的计算开销,而车间里相机位置和 ROI 区域固定,输入尺寸完全可以是静态的。

导出后再做 int8 量化。树莓派 5 的 CPU 对 int8 算子有优化,实测同一模型在 640x640 输入下,FP32 推理约 2.5 秒一帧,int8 量化后能缩短到 0.8 秒左右。量化方法用 ONNX Runtime 自带的quantize_dynamic工具即可,不需要额外训练。量化后精度会掉一点,但缺陷检测场景里主要看漏检率,我用现场采集的 300 张图测过,mAP 从 0.951 降到 0.936,漏检没有增加,这个损失完全可以接受。

2.3 实测推理性能与优化思路

说一下真实数据。树莓派 5 跑 YOLOv5s,640x640 输入,单线程 FP32,大约 2~3 FPS;int8 量化后大约 5~8 FPS。如果继续把输入降到 320x320,int8 模式下能到 12 FPS 左右。

单看这个帧率,很多人会觉得不够用。但产线视觉检测和娱乐玩模型不同:相机是固定机位,产品经过时只需要在特定位置抓拍,再对抓拍图像做推理。我最终实现的方式是传感器触发拍照,然后把 ROI 区域裁剪出来,只对裁剪后的图像推理。这样单帧处理时间在 80 毫秒以内,完全满足现场节拍。

优化思路总结成一句话:不要把整个画面丢给模型,先做 ROI 定位,再做推理。树莓派的算力就那么点,省下来的算力比提升硬件更划算。

2.4 内存不足与 Swap 的救与坑

跑 YOLOv5 过程中出现最多的报错是Killed或Segmentation fault,很多情况下不是代码问题,而是内存不足。8GB 内存在加载图像、跑 ONNX、开视频流之后,剩余空间很紧张。

我的做法是增加一个 swap 文件,但不放在 SD 卡上,而是加了一个 USB 接口的小容量 SSD(后面章节会细说启动盘方案)。Swap 大小设为 4GB,并把系统默认的vm.swappiness从 60 改到 10,意思是不到万不得已不主动用 swap,避免频繁交换把存储写坏。

如果你必须用 SD 卡跑,那 swap 文件要谨慎,因为频繁写入会明显缩短 SD 卡寿命,而且掉电后 swap 数据残留可能导致下次开机文件系统检查异常。

3. 供电是硬门槛:车间里的小电压波动

3.1 树莓派 5 对电源的要求比想象中高

树莓派 5 的接口是 USB-C,但它的电源需求比手机充电头高得多。官方建议使用 5V/5A(即 PD 协议 25W)或至少 5V/3A 的高质量电源。我用一个旧款 5V/2A 充电头做过测试,接入 USB 摄像头和风扇后,系统日志里反复出现Under-voltage detected,紧接着 CPU 频率被强制压低,推理速度掉了将近一半。

所以,供电这块不能省。我在车间用了官方 27W USB-C 电源,实测电压稳定在 5.1V 左右。注意要买正品,市面上很多标称 5V/5A 的电源实际带负载能力很差,接上设备电压就掉到 4.8V 以下,比普通充电头更容易出问题。

3.2 车间电网波动与应对方案

车间电网和办公室不一样,大电机启动、电焊机作业都会让电压瞬间波动。树莓派 5 虽然抗造,但长时间在欠压状态下运行,SD 卡出现坏块的几率大增。

我的处理方式是在设备电源前端加了一个小型 UPS,不需要很大功率,只给树莓派、摄像头和一块小交换机使用就行。UPS 的作用不是提供多长续航,而是把电压波动“抹平”,让树莓派不直接面对车间电网的毛刺。实测在电机启动导致车间照明灯闪烁的情况下,树莓派日志不再出现电压警告。

如果预算不宽裕,至少别把树莓派和电焊机、大功率设备插在同一个插排上,尽量从不同回路取电。

3.3 电源线材容易翻车

这个坑很隐蔽。树莓派 5 用 PD 快充协议时,线材必须能承载 5A 电流,也就是需要带 E-Marker 芯片的线。普通手机数据线虽然接口一样,但线芯细、压降大,满载时供电电压可能直接跌破 4.5V。

我最初用了一根 1.5 米的普通 USB-C 线,系统负载一高就重启。换成 20 厘米长、标注支持 5A 的短线后,问题消失。结论是线越短越好,别为了布线方便用长线,电压降带来的问题比布线难处理得多。

4. 散热是最大基建问题

4.1 满负荷温度实测

树莓派 5 的性能释放建立在主动散热前提下,这是它与前代产品一个非常明显的区别。裸芯片跑 YOLOv5 连续推理,我测过 30 分钟,结温直接冲到 88°C,接近 100°C 的降频阈值。

系统一旦降频,推理速度会从 2~3 FPS 掉到 1.4 FPS 左右,而且不是线性下降,是断崖式的。放在车间这种环境里,夏天车间温度可能到 35°C,情况会更糟。所以我建议没有散热方案的不要尝试长时间跑推理,性能数据会骗人。

4.2 散热方案与风扇策略

我最终用的是官方主动冷却器,就是带涡轮风扇和散热片的那款。安装后满载温度能控制在 55°C 左右,性能不再掉链子。如果不想用官方方案,至少也要 2U 散热片加 5V 风扇,并确保风道通畅。

风扇策略也值得调整。官方散热器的风扇默认由固件控制,但 Ubuntu 下温度阈值可以手动改。我的思路是让风扇在 50°C 以下不转,60°C 以上满转,这样既减少粉尘吸入,又降低噪音。具体控制用pinctrl-fan或者直接在系统服务里写个温度监控脚本,每隔 10 秒读一次vcgencmd measure_temp,根据温度写/sys/class/thermal/cooling_device0/cur_state。

实际测试下来,风扇策略对可靠性影响很大。车间粉尘比较多,如果风扇全程满转,吸入的粉尘很快就会把散热片堵住;设置一个温度滞回区间,让风扇只在需要时高速旋转,能明显延长维护周期。

4.3 温度监控日志

用温度监控脚本把数据写入本地文件即可,最好每小时生成一个 CSV。车间里设备多,一旦产品检测不准,先看温度曲线能快速判断是不是热降频导致的推理质量下降。有时候软件怎么调都没问题,最后发现是散热赌了,这种排查经历一次就终生难忘。

5. 网络与远程:摆脱不了的那根网线

5.1 车间里的 WiFi 为什么难用

车间环境对无线网络非常不友好:金属结构遮挡多,2.4GHz 频段干扰严重,5GHz 穿墙又弱。树莓派 5 的 WiFi 性能不差,但在车间角落实测丢包率很高,SSH 经常断线。更麻烦的是,如果 WiFi 信号时好时坏,远程看到的是服务还在跑,但程序已经卡在等待网络响应上。

我的建议是能用网线就一定要用网线。树莓派 5 的千兆以太网口可靠性远高于 WiFi,而且在无人值守场景下,网线少一层“重连”逻辑,程序逻辑也简单。如果工位真的拉不了网线,可以加一台 WiFi 中继器放在离树莓派较近的位置,至少保证信号强度。

5.2 远程维护方式

车间设备在产线旁,人在办公室,远程维护基本靠 SSH。我在 Ubuntu 里开启了 sshd,并且把设备 IP 设为静态,避免重启后地址变化找不到设备。

如果需要看图像调试,可以临时启 VNC,但我不建议长期开图形界面。实际调试时我常用的是 SSH 端口转发看程序日志,以及定时把检测结果图片保存到共享目录,在办公室用图片辅助判断。这种“只看结果不看现场”的思路,比天天盯远程桌面高效。

还有一点:远程操作涉及公网暴露的要格外谨慎。车间设备不要直接在路由器上设置端口映射暴露到公网,能走公司内网就走内网,远程维护工具尽量只监听内网地址。

5.3 网络异常自动恢复脚本

设备长时间运行后,偶尔会遇到“网卡活着但路由不通”的假死状态。我写了一个简单的看门狗脚本,每两分钟 ping 一次网关,连续三次不通就重启网络服务:

#!/bin/bash if ! ping -c 1 -W 2 192.168.1.1 > /dev/null 2>&1; then ((fail_count++)) else fail_count=0 fi if [ $fail_count -ge 3 ]; then sudo systemctl restart systemd-networkd fail_count=0 fi

用 systemd timer 定时执行,效果很好。这个脚本的逻辑很朴素,但它能避免很多“人不在现场、远程又连不上”的尴尬。

6. 断电重启后,一切都要自动回来

6.1 systemd 自启服务写法

树莓派放在产线旁,最怕的不是程序宕掉,而是断电之后没人去按开机键。树莓派本身接上电就会开机,关键是开机后检测服务能不能自己跑起来。

我用 systemd 管理推理服务,单元文件写得很简单:

[Unit] Description=YOLO Detection Server After=network-online.target Wants=network-online.target [Service] User=pi WorkingDirectory=/opt/yolo Environment="PYTHONPATH=/opt/yolo" ExecStart=/home/pi/yolo_env/bin/python /opt/yolo/main.py --config config.yaml Restart=always RestartSec=5 [Install] WantedBy=multi-user.target

需要注意两点:一是After=network-online.target保证网络起来后再启动服务,否则摄像头 IP 还没就绪程序就报错;二是Restart=always加上RestartSec=5,防止程序因偶发问题退出后不再回来。

在服务里加一个日志输出,让journalctl能记录检测结果和错误。我习惯用一个独立日志文件记录每一帧的检测结果,方便回溯。

6.2 保护 SD 卡:日志挂 tmpfs

树莓派 5 长时间运行,最大的敌人是 SD 卡频繁写入。YOLO 程序每帧保存检测结果图片,加上系统日志,一张普通 SD 卡很可能在几个月内写坏。我做了三件事:

第一,所有检测结果图片和日志都写到/var/log和/tmp之外的独立目录,但如果写入量大,还是会伤卡。所以在条件允许的情况下,我把日志目录挂载为 tmpfs,也就是直接用内存暂存,系统重启就清空,避免频繁写盘。

第二,用 logrotate 限制日志文件大小,超过 5MB 就轮转,保留最近 10 份。这个配置能防止日志文件无限增长,拖垮 SD 卡。

第三,如果你像我一样用 SSD 作为系统盘,把/放 SSD,SD 卡只用于 boot 分区和固件,那么 SD 卡写入量会大大减少,可靠性提升明显。树莓派 5 支持 USB 启动,用一条 USB 转 M.2 硬盘盒加一块 128GB 小容量 SSD,成本不高,但解决了很多烦恼。

6.3 掉电后的恢复逻辑

树莓派意外断电再上电后,程序自动启动只是第一步,真正的坑在于一些残留状态文件。例如上次运行生成的摄像头锁文件、临时共享内存段,会影响新进程的初始化。我的解决方式是在服务启动前,先在 systemd 里加一个ExecStartPre命令,清理/tmp下的旧文件:

ExecStartPre=/bin/sh -c "rm -f /tmp/yolo_*.lock /dev/shm/yolo_*"

另外,摄像头设备的枚举顺序在断电后可能变化。USB 相机有时会占用不同的/dev/video*节点,如果程序写死了/dev/video0,重启后可能找不到设备。我在程序里加了设备名匹配逻辑,扫描/dev/video*,挑选包含相机型号信息的那个节点,而不是写死编号。

最后建议部署前做一次“拔电源测试”,连续拔插几次,观察每次开机后服务是否都能在 2 分钟内恢复正常。这一步能暴露很多看似不起眼、但实际运行中极难排查的问题。

最后说点题外话

这套设备在车间连续跑了大几周,真正让我安心下来的不是树莓派 5 算力有多强,而是那些看起来琐碎的基建问题都被填平了。供电用一个靠谱的电源和 UPS,散热装上主动冷却并定期清灰,网络乖乖走网线,系统做到断电自启,这些工作说起来不起眼,但每一件都可能让整个项目从“技术可行”变成“上线就挂”。

如果后续要多工位复制,我建议先别急着买一堆树莓派堆算力,把当前这套装置的坑填平,运行一个月没有大问题,再照着同一套方案复制。边缘视觉部署从来不是跑通一个模型就算胜利,让模型在车间里稳定输出结果,才是真正值得花时间的地方。

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

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

立即咨询