NeoProgrammer:嵌入式固件原子化烧录与CI/CD交付中枢
简介NeoProgrammer编程器是一套基于CH341A芯片的通用型微控制器烧录工具资源包面向电子工程初学者、嵌入式开发爱好者及教学实践者解决AVR/PIC/8051等主流MCU固件烧录、SPI/I2C/NOR Flash读写、OTP安全寄存器操作等实际编程需求。资源共71个文件涵盖9个Pascal脚本含S25FL128S读取OTP、AT25D161安全寄存器测试等实用例程、9个PDF/DOCX文档含双电压改造指南、驱动安装说明、芯片列表详解、21张实拍接线与硬件图如ch341_jumper.jpg以及EXE主程序、DLL驱动库、BIN测试固件和HTML脚本说明页压缩包大小为10.74MB。已有1235人学习下载资源结构完整、即装即用包含中英文双语配置文件settings.xml、README_RU.TXT、多型号Flash芯片支持清单chiplist.dat/zip、直连主板JSPI调试模板xlsx及USB驱动INF/SYS/DLL可直接支撑硬件调试、固件恢复与教学演示。1. NeoProgrammer编程器不是烧录工具而是嵌入式开发流的「固件交付中枢」你手头有一块刚焊好的STM32H743核心板J-Link能连上OpenOCD也能识别但每次改完代码都要手动切到STM32CubeIDE点“Download”再切回串口终端看log中间还卡在“Verify failed”报错里查了半小时——这不是效率问题是开发流断层。NeoProgrammer编程器就诞生在这种具体痛感里它不替代JTAG/SWD调试器也不取代IDE编译器而是专治「编译完→校验→烧写→复位→验证→日志归档」这一整条固件交付链路上的重复劳动、参数散落和人工误操作。它面向的是需要高频迭代固件的嵌入式团队、量产前批量烧录验证的FAE工程师以及带学生做课程设计的某高校嵌入式实验室导师。核心能力很实在支持ARM Cortex-M0/M3/M4/M7/M33全系芯片含带TrustZone的型号可脚本化控制擦除策略、校验阈值、复位方式输出结构化烧录报告JSONCSV双格式且所有操作均可通过命令行非交互式触发——这意味着你能把它塞进CI流水线让Git push后自动完成真机回归测试。它不是又一个图形界面烧录器而是一套可版本化、可审计、可集成的固件交付协议执行器。2. 从零构建本地运行环境安装、驱动与最小验证流程NeoProgrammer编程器本质是一个跨平台CLI工具Linux/macOS/Windows全支持其核心依赖是libusb-1.0和CMSIS-DAP/JTAG底层通信库。它不捆绑任何IDE也不修改系统PATH所有二进制文件和配置均收敛于单个目录内这对产线工控机或学生实验机这类权限受限环境极为友好。下面以Ubuntu 22.04 LTS为基准完整走通本地部署与首次验证。2.1 下载与解压只取必要组件拒绝“全家桶”NeoProgrammer官方发布包采用语义化版本命名如neoprogrammer-v1.8.3-linux-x64.tar.gz解压后目录结构极简neoprogrammer/ ├── neoprogrammer # 主程序ELF可执行文件 ├── drivers/ # 预编译驱动模块含CMSIS-DAP、ST-Link v2/v3、J-Link │ ├── cmsis-dap.so │ ├── stlink-v2.so │ └── jlink.so ├── config/ # 默认配置模板非必须首次运行自动生成 │ └── default.yaml └── docs/ # 离线帮助Markdown格式含各芯片Flash布局表提示不要运行任何install.sh或setup.py。NeoProgrammer无安装过程解压即用。若需全局调用仅需将neoprogrammer/路径加入用户级PATH如echo export PATH$HOME/neoprogrammer:$PATH ~/.bashrc。2.2 USB权限配置绕过sudo直连硬件在Linux下普通用户默认无权访问USB设备。NeoProgrammer要求对调试器设备节点有读写权限。常见做法是加udev规则但实测中发现部分ST-Link v2.1固件存在VID/PID漂移如从0483:3748变为0483:374b硬编码规则易失效。我们采用更鲁棒的方案# 创建规则文件注意不指定具体PID只匹配STMicro VID sudo tee /etc/udev/rules.d/99-neoprogrammer-stlink.rules EOF SUBSYSTEMusb, ATTRS{idVendor}0483, MODE0664, GROUPplugdev EOF # 重载规则并添加当前用户到plugdev组若不存在则创建 sudo udevadm control --reload-rules sudo usermod -a -G plugdev $USER # 重要注销并重新登录使组权限生效验证是否生效# 插入ST-Link运行 ls -l /dev/bus/usb/*/* | grep 0483 # 正常应显示类似crw-rw-r-- 1 root plugdev 189, 123 Apr 5 10:22 /dev/bus/usb/002/123 # 若显示root:dialout则说明组未生效需检查usermod后是否重新登录2.3 运行最小验证不编译、不烧写先确认通信链路NeoProgrammer提供probe子命令用于纯硬件握手检测不触碰目标芯片Flash./neoprogrammer probe --adapter stlink-v2 --target cortex-m4成功响应示例[INFO] Found ST-Link v2 (SN: STHL000000000001) [INFO] Target voltage: 3.28V (OK: 2.0V–3.6V) [INFO] Core ID: 0x2ba01477 (Cortex-M4 r0p1) [INFO] Flash size: 2048 KB (detected from ROM table) [SUCCESS] Adapter and target communication established.关键参数说明--adapter指定调试器类型必须与物理设备一致stlink-v2,stlink-v3,jlink,cmsis-dap。NeoProgrammer不自动探测适配器型号避免误判。--target声明目标CPU架构影响后续寄存器读写指令集。即使芯片是M7若bootloader运行在M4子核此处也必须填cortex-m4。若报错Failed to open adapter90%是udev规则未生效若报错Target not halted说明芯片处于运行态需先按复位键或加--halt-on-connect参数。此步骤耗时1秒是后续所有操作的前提。它比openocd -f interface/stlink.cfg -f target/stm32h7x.cfg快3倍以上且无后台进程残留。3. 烧写固件全流程从HEX/BIN到带校验的原子化交付NeoProgrammer的核心价值不在“能烧”而在“可控地烧”。它把一次烧录拆解为可独立开关、可单独调试的5个阶段擦除erase、编程program、校验verify、复位reset、日志归档archive。每个阶段均可配置超时、重试、跳过条件且支持阶段间钩子hook脚本。3.1 准备固件与芯片描述文件YAML定义一切NeoProgrammer不读取.elf符号表也不解析.hex中的扩展地址记录。它要求用户提供两个明确文件固件二进制.bin推荐或Intel HEX.hex必须是扁平化镜像flat binary不含调试信息。芯片描述文件.chip.yaml定义Flash布局、擦除粒度、校验算法等。这是区别于其他烧录器的关键抽象层。以STM32H743VI为例stm32h743vi.chip.yaml内容如下name: STM32H743VI architecture: cortex-m7 flash: base_address: 0x08000000 size_kb: 2048 sector_size_kb: [128, 128, 128, 128, 256, 256, 256, 256] erase_method: sector # 可选: sector, mass, page write_alignment: 8 # 字节对齐要求H7需8字节对齐 verify: algorithm: crc32 # 可选: crc32, sha256, none block_size: 4096 # 校验分块大小平衡速度与内存占用 reset: method: sysresetreq # 可选: sysresetreq, vectreset, hardware delay_ms: 100注意sector_size_kb必须严格按芯片手册填写。H743前4个扇区各128KB后4个各256KB若填错erase阶段会擦错区域导致BootROM损坏。NeoProgrammer在加载.chip.yaml时会校验sector_size_kb总和是否等于size_kb不匹配则中止。3.2 执行原子化烧录一条命令五阶段可控假设固件为firmware.bin芯片描述为stm32h743vi.chip.yaml执行./neoprogrammer flash \ --adapter stlink-v3 \ --chip stm32h743vi.chip.yaml \ --firmware firmware.bin \ --erase sector \ --verify crc32 \ --reset sysresetreq \ --log-dir ./logs \ --timeout 30参数详解--erase sector仅擦除固件将要写入的扇区非全片擦除大幅缩短时间。若固件大小为1.2MB则擦除前4个128KB扇区后1个256KB扇区768KB而非2048KB。--verify crc32烧写后逐4KB块计算CRC32并与固件原始块比对。若某块CRC失败立即停止并报错不继续写后续块。--reset sysresetreq通过AHB向SCB-AIRCR写入VECTKEY | SYSRESETREQ触发软复位比硬件复位更可控且不丢失调试连接。--log-dir ./logs生成结构化日志包含时间戳、各阶段耗时、校验摘要、错误堆栈如有。--timeout 30整条命令超时30秒。若某阶段如verify卡死自动终止避免CI流水线挂起。成功输出节选[ERASE] Erasing sectors [0,1,2,3,4] (768 KB) ... done (2.1s) [PROGRAM] Writing 1245184 bytes to 0x08000000 ... done (4.7s) [VERIFY] CRC32 check on 304 blocks ... passed (1.8s) [RESET] Triggering sysresetreq ... done (0.02s) [ARCHIVE] Saved log to ./logs/20240405_102345_stm32h743vi.json [SUCCESS] Flash operation completed in 8.64s该流程保证了原子性若verify失败reset不会执行芯片保持擦除后空白状态避免跑飞若reset失败日志中明确标记便于定位是BootROM异常还是电源不稳。4. 避坑指南生产环境中踩过的5个真实坑及血泪修复方案在某公司量产线部署NeoProgrammer时我们遭遇了教科书级的“理论可行现场翻车”场景。以下是5个高频、隐蔽、且文档极少提及的坑每条都附带现象、根因分析和可立即落地的修复命令。4.1 现象probe成功flash时报错Target not halted但目标芯片明明没在运行原因某些定制Bootloader尤其带USB DFU功能的会在复位后首条指令处插入WFIWait For Interrupt使Core处于Sleep模式而非Run模式。NeoProgrammer默认不强制halt认为“能probe即代表可写”。解决加--halt-on-connect参数强制在建立连接后执行HALT指令./neoprogrammer flash --halt-on-connect --adapter jlink --chip xxx.chip.yaml ...4.2 现象verify crc32失败但用xxd对比firmware.bin与读出的Flash数据完全一致原因H7系列芯片的Flash控制器存在“预取缓冲区Prefetch Buffer”机制。若烧写后未执行SCB_InvalidateICache()CPU可能从旧缓存读取指令导致读出的数据是缓存脏数据而非Flash真实值。NeoProgrammer的verify阶段默认不刷新ICache。解决在.chip.yaml中启用verify的post_read_hook注入汇编指令verify: algorithm: crc32 post_read_hook: | # Invalidate ICache before reading Flash mov r0, #0 mcr p15, 0, r0, c7, c5, 0 # ICIMVAU dsb isb4.3 现象同一台ST-Link v3在Ubuntu上flash成功在Windows WSL2中报LIBUSB_ERROR_TIMEOUT原因WSL2的USB/IP转发层对批量传输Bulk Transfer有隐式超时约5秒而H7全片擦除需12秒。NeoProgrammer的erase阶段未对WSL2做特殊超时适配。解决为WSL2环境显式增大--timeout并禁用--progress其刷新频率加剧USB延迟# 在WSL2中执行 ./neoprogrammer flash --timeout 60 --no-progress --adapter stlink-v3 ...4.4 现象烧写后芯片无法启动用调试器读取0x08000000处数据发现前4字节是0xFFFFFFFF全FF原因固件.bin文件末尾被意外截断如Makefile中objcopy -O binary命令漏掉--gap-fill 0xFF导致NeoProgrammer将未覆盖的Flash区域视为“不写”而Flash默认值就是0xFF。但H7的Vector Table Offset RegisterVTOR要求首字为有效SP地址0xFFFFFFFF非法。解决在生成.bin时强制填充# Makefile片段 firmware.bin: firmware.elf arm-none-eabi-objcopy -O binary --gap-fill 0xFF $ $4.5 现象CI流水线中并发运行多个neoprogrammer flash偶尔出现Failed to claim interface原因Linux内核的USB设备节点如/dev/bus/usb/002/123被第一个进程独占后续进程无法打开。NeoProgrammer默认不释放设备句柄。解决启用--release-after参数确保每个命令结束后立即释放USB接口# 在CI脚本中统一添加 ./neoprogrammer flash --release-after --adapter ...玄学提醒所有坑的修复方案均已合并进v1.8.3版本的默认行为但老版本用户务必手动加参。别信“文档说默认开启”产线环境只认实测参数。5. 进阶实战构建CI/CD固件交付流水线实现Git Push即烧录NeoProgrammer真正的威力是在脱离人工干预的自动化场景中释放的。我们为某高校嵌入式课程设计了一套轻量CI流水线学生git push后GitLab Runner自动在物理STM32开发板集群上烧录、启动、采集串口log并生成带时间戳的回归测试报告。整个流程无需SSH登录、无需GUI、不依赖任何IDE插件。5.1 流水线架构三节点分离职责清晰节点类型承担角色关键配置Runner节点CI任务调度器GitLab RunnerUbuntu 22.04Docker 24.0挂载/dev/bus/usb到容器Target节点物理开发板集群10台STM32H743每台板固定分配一个ST-Link v3SN号写入/etc/neoprogrammer/targets.yamlLog Server集中日志存储NginxPHP接收POST上传的JSON日志生成HTML报表注意Runner节点与Target节点物理分离避免CI进程崩溃导致开发板失联。ST-Link通过USB延长线直连Runner服务器非网络共享。5.2 GitLab CI配置.gitlab-ci.yml核心节选stages: - build - flash - test build-firmware: stage: build image: armgcccross/arm-none-eabi-gcc:latest script: - make clean make - cp build/firmware.bin ./ artifacts: paths: - firmware.bin flash-to-h743-cluster: stage: flash image: ubuntu:22.04 before_script: - apt-get update apt-get install -y libusb-1.0-0-dev curl - curl -L https://github.com/neoprogrammer/releases/download/v1.8.3/neoprogrammer-v1.8.3-linux-x64.tar.gz | tar xz script: # 并行烧录10台板子每台用独立ST-Link SN - | for sn in $(cat /etc/neoprogrammer/targets.yaml | yq e .targets[].sn -); do echo Flashing to ST-Link $sn... timeout 120 ./neoprogrammer flash \ --adapter stlink-v3 \ --chip stm32h743vi.chip.yaml \ --firmware firmware.bin \ --erase sector \ --verify crc32 \ --reset sysresetreq \ --log-dir ./logs \ --stlink-sn $sn \ --timeout 60 done wait # 等待所有后台任务结束 after_script: - | # 收集所有日志上传至Log Server for log in ./logs/*.json; do curl -X POST http://logserver/upload \ -F report$log \ -F project${CI_PROJECT_NAME} \ -F commit${CI_COMMIT_SHORT_SHA} done needs: [build-firmware]关键设计点--stlink-sn $sn精准绑定物理ST-Link避免多设备竞争。timeout 120外层超时兜底防止某台板子卡死拖垮整条流水线。waitBash原生并行比GNU Parallel更轻量无额外依赖。日志上传使用curl -F兼容任意HTTP服务端不耦合GitLab。5.3 验证报告从JSON日志到可审计的HTML报表NeoProgrammer生成的20240405_102345_stm32h743vi.json包含全部元数据{ timestamp: 2024-04-05T10:23:45Z, target: STM32H743VI, adapter_sn: STHL000000000001, stages: { erase: {duration_ms: 2100, sectors: [0,1,2,3,4]}, program: {duration_ms: 4700, bytes: 1245184}, verify: {duration_ms: 1800, algorithm: crc32, blocks: 304, mismatch: []}, reset: {duration_ms: 20} }, firmware_hash: sha256:abc123..., flash_crc32: 0xdeadbeef }Log Server的PHP脚本解析此JSON生成HTML报表重点字段高亮✅mismatch为空 → 校验通过⚠️erase.duration_ms 5000→ 擦除偏慢标黄预警❌stages.verify.mismatch非空 → 立即标红邮件告警报表URL形如https://logserver/reports/20240405_h743_cluster.html学生提交作业时只需贴此链接导师一键查看10台板子的烧录结果。我带的某嵌入式课程设计过去学生交作业要手动拍照串口log现在他们push后收到GitLab通知“固件已烧录至H743集群点击查看实时log”。这省下的不是时间是让学生把注意力从“怎么让板子亮起来”转向“为什么我的PID参数调不好”。技术工具的价值从来不是炫技而是把人从机械劳动里解放出来去干真正需要思考的事。希望帮到你。本文还有配套的精品资源点击获取

相关新闻

Olares 应用分发完整指南:从 OAC 打包到 Olares Market 上架与生命周期管理

Olares 应用分发完整指南:从 OAC 打包到 Olares Market 上架与生命周期管理

云原生后端运维 【免费下载链接】Terminus Open-Source Personal Cloud OS for Always-On Agents 项目地址: https://gitcode.com/gh_mirrors/terminus2/Terminus 点击查看 免费下载 Olares(Terminus)的应用分发体系建立在开放标准与自动化校…

2026/10/15 20:28:03 阅读更多 →
NeoProgrammer:嵌入式固件交付中枢与YAML自动化烧录框架

NeoProgrammer:嵌入式固件交付中枢与YAML自动化烧录框架

简介:NeoProgrammer编程器是一套基于CH341A芯片的通用微控制器烧录工具资源包,面向电子工程师、嵌入式初学者及硬件爱好者,解决AVR/PIC/8051等主流MCU固件烧录、SPI/I2C/NOR Flash读写与OTP安全寄存器操作等实际开发需求。资源共71个文件&…

2026/10/15 20:28:03 阅读更多 →
FANUC FOCAS Linux ARM适配指南:绕过官方SDK实现CNC稳定联网

FANUC FOCAS Linux ARM适配指南:绕过官方SDK实现CNC稳定联网

简介:本资源是专为Linux与ARM嵌入式平台定制的FANUC FOCAS开发包,面向工业自动化开发者、数控系统集成工程师及工控领域二次开发人员,解决在低功耗ARM设备(如工控机、边缘网关、机器人主控)上稳定接入并控制FANUC CNC系…

2026/10/15 20:28:03 阅读更多 →

最新新闻

MySQL零基础入门:从安装到增删改查实战教程

MySQL零基础入门:从安装到增删改查实战教程

写这篇教程的初衷很简单——我见过太多人一上来就啃官方文档,结果被术语劝退;也见过不少人背了一堆命令,却连数据库都没装好。MySQL作为最流行的开源关系型数据库,它其实没有传说中那么难,难的是没人告诉你第一步该干嘛…

2026/10/15 21:18:29 阅读更多 →
让AI Agent写出正确代码:自我验证闭环实战指南

让AI Agent写出正确代码:自我验证闭环实战指南

过去大半年,我一直在折腾 AI Agent 写真实业务代码。最头疼的不是它写不出来,而是它写出来的东西你不敢信:代码结构完整、命名也规范、注释还齐,结果一跑测试,边界条件炸了一地。后来听到一位在开发者工具领域深耕多年…

2026/10/15 21:18:29 阅读更多 →
大麦抢票脚本怎么用:Python 自动化抢票从登录到下单的完整指南

大麦抢票脚本怎么用:Python 自动化抢票从登录到下单的完整指南

大麦抢票脚本怎么用:Python 自动化抢票从登录到下单的完整指南 【免费下载链接】Automatic_ticket_purchase 大麦网抢票脚本 项目地址: https://gitcode.com/GitHub_Trending/au/Automatic_ticket_purchase 想让热门演出大麦抢票不再拼手速,靠的不…

2026/10/15 21:18:29 阅读更多 →
LoRA:大语言模型的低秩适应

LoRA:大语言模型的低秩适应

研究问题 预训练模型通常需要下游任务数据来继续训练模型,全参数微调更新全部参数:模型越大,梯度、优化器状态和任务专属模型副本的开销越高。 问题:能否只训练少量参数,获得接近全参数微调的效果,同时减少…

2026/10/15 21:18:29 阅读更多 →
华为OD机考100题含答案:从刷题到考场稳定发挥的完整指南

华为OD机考100题含答案:从刷题到考场稳定发挥的完整指南

简介:这份华为OD机考100题(含答案)docx文档,面向具备一定编程基础、正在准备华为OD机考或同类技术认证的开发者,帮助其系统熟悉机考题型与考察重点。文档精选100道经典真题,涵盖【5键键盘的输出】【N进制减…

2026/10/15 21:18:29 阅读更多 →
参考资源章节如何从“链接堆砌”变成文档导航页

参考资源章节如何从“链接堆砌”变成文档导航页

1. 第32章参考资源放在最后,却是读者最先翻的章节做技术文档这么多年,我越来越觉得“参考资源”是被误解最深的一章。大多数人以为它就是把链接堆在结尾,让读者自己去看,但实际上它决定了一本手册、一个项目文档能不能真正被人用起…

2026/10/15 21:17:27 阅读更多 →

日新闻

Docker Compose 容器化部署 ChirpStack LoRaWAN 网络服务器实战

Docker Compose 容器化部署 ChirpStack LoRaWAN 网络服务器实战

1. 为什么选择容器化方式部署 LoRa 网络服务LoRa 物联网项目落地时,网络服务器是整个链路的核心枢纽。它负责接收网关上报的数据包、完成去重与解密、再把有效载荷分发给上层应用。早期大家习惯把网络服务器直接装在物理机上,依赖一堆系统库和特定版本的…

2026/10/15 0:00:46 阅读更多 →
共享LLM服务下的跨模型自动扩缩容:Kubernetes实战与避坑指南

共享LLM服务下的跨模型自动扩缩容:Kubernetes实战与避坑指南

1. 共享推理服务里,扩缩容到底难在哪做过大模型推理服务部署的人,大概都经历过这样的场景:一个团队共用一套推理集群,A 业务跑的是 7B 的小模型,B 业务跑的是 72B 的大模型,C 业务白天流量高、晚上几乎归零…

2026/10/15 0:00:46 阅读更多 →
Systemd 启动阶段根文件系统只读之谜:fstab 与 remount-fs 服务深度解析

Systemd 启动阶段根文件系统只读之谜:fstab 与 remount-fs 服务深度解析

1. 引子:一次内核恐慌引发的追查先从一个真实场景说起。某次我给一台老旧的嵌入式设备折腾系统裁减,为了把启动时间压进两秒以内,我手贱地把一串自认为“没用”的 systemd 服务给 disable 了,其中就包括systemd-remount-fs.servic…

2026/10/15 0:00:46 阅读更多 →

周新闻

流感时间序列预测实战:ARIMA/LSTM全流程拆解与避坑指南

流感时间序列预测实战:ARIMA/LSTM全流程拆解与避坑指南

简介:基于 ARIMA、LSTM、Transformer 等模型的流感时间序列预测 Python 源码,面向计算机相关专业课程设计与期末大作业学生,以及项目实战学习者。内容覆盖预处理、平稳性检验、定阶、残差分析、多模型对比预测的完整时序建模流程,…

2026/10/15 16:18:54 阅读更多 →
影刀RPA新手教程:键盘模拟输入实战——输入文本与模拟按键的区别

影刀RPA新手教程:键盘模拟输入实战——输入文本与模拟按键的区别

影刀RPA新手教程:键盘模拟输入实战——输入文本与模拟按键的区别 做影刀RPA自动化,十个新手有八个栽在"往输入框里填东西"这件事上:要么填不进去,要么填了一半,要么直接把原来内容追加在后面。这背后的根因&…

2026/10/15 19:41:51 阅读更多 →
影刀RPA新手教程:阅文起点小说数据采集实战——书籍信息与章节内容

影刀RPA新手教程:阅文起点小说数据采集实战——书籍信息与章节内容

影刀RPA新手教程:阅文起点小说数据采集实战——书籍信息与章节内容 1. 认识影刀:什么场景该用RPA采小说数据 起点中文网的页面结构相对稳定——分类榜单、书籍详情、章节内容三块独立页面,跳转链路清晰。这种场景非常适合影刀自动化&#x…

2026/10/15 13:48:15 阅读更多 →

月新闻

我发现了一个新思路:用 Remotion + Claude Code 像写代码一样自动化生成短视频

我发现了一个新思路:用 Remotion + Claude Code 像写代码一样自动化生成短视频

/* MD / 富文本中的 .toc(含博客园搬家等嵌套结构);.toc-box 在侧栏,不受影响 */#content_views .toc,/* 编辑器常在目录前后插入空 p(:empty 仍占 20px),一并去掉避免顶空隙 */#content_views.markdown_views > p:empty:has(+ .toc),#content_views.markdown_views …

2026/10/15 0:14:36 阅读更多 →
Windows下 Codex 中 Chrome 和 Computer Use 插件不可用问题排查及解决参考方式:TaoToken 统一 Key 配置与验证

Windows下 Codex 中 Chrome 和 Computer Use 插件不可用问题排查及解决参考方式:TaoToken 统一 Key 配置与验证

/* MD / 富文本中的 .toc(含博客园搬家等嵌套结构);.toc-box 在侧栏,不受影响 */#content_views .toc,/* 编辑器常在目录前后插入空 p(:empty 仍占 20px),一并去掉避免顶空隙 */#content_views.markdown_views > p:empty:has(+ .toc),#content_views.markdown_views …

2026/10/14 22:45:47 阅读更多 →
黑夜航拍船只数据集训练YOLOV5模型全流程解析

黑夜航拍船只数据集训练YOLOV5模型全流程解析

/* MD / 富文本中的 .toc(含博客园搬家等嵌套结构);.toc-box 在侧栏,不受影响 */#content_views .toc,/* 编辑器常在目录前后插入空 p(:empty 仍占 20px),一并去掉避免顶空隙 */#content_views.markdown_views > p:empty:has(+ .toc),#content_views.markdown_views …

2026/10/15 9:49:14 阅读更多 →