Linux系统启动脚本/etc/rc.local配置全解析与Systemd兼容实践
1. 项目概述为什么我们今天还要聊 /etc/rc.local如果你是一个Linux系统管理员或者是一个需要在服务器上部署自研服务的开发者你大概率遇到过这样的需求如何在系统启动时自动运行一个脚本、启动一个后台服务或者设置一个特定的环境变量在众多解决方案中/etc/rc.local这个文件就像一个“老熟人”它简单、直接几乎在所有主流的Linux发行版中都占有一席之地。但你可能也听过一些声音说它“过时了”、“不推荐使用”尤其是在Systemd成为主流的今天。那么我们还有必要深入了解它吗答案是肯定的。理解/etc/rc.local的配置流程不仅是为了处理那些遗留系统或特定场景更是为了透彻理解Linux系统启动的演进脉络和不同初始化系统的设计哲学。当你面对一台老旧但仍在服役的CentOS 6服务器或者需要在一些嵌入式、定制化的Linux环境中进行配置时rc.local的知识就是你的救命稻草。本文将从一个一线运维和开发者的角度手把手拆解/etc/rc.local的配置全流程从它的历史地位、工作原理到具体的配置步骤、排错技巧以及在现代Systemd体系下的兼容性方案让你真正掌握这个经典工具。2. rc.local 的前世今生从SysVinit到Systemd的桥梁要正确使用一个工具首先要理解它从何而来为何存在。/etc/rc.local文件根植于传统的SysVinit初始化系统。在那个时代系统启动过程被划分为不同的运行级别Runlevel每个级别对应一组需要启动或停止的服务。/etc/rc.d/rc这个主脚本会根据指定的运行级别执行对应目录如/etc/rc.d/rc3.d/下的所有脚本。这些脚本通常以SStart或KKill开头后面跟着一个数字序号和服务的名字。那么/etc/rc.local处在什么位置呢它通常是最后一个被执行的脚本。在所有的系统服务、网络、守护进程都按照既定顺序启动完毕后rc.local才粉墨登场。它的设计初衷非常明确为系统管理员提供一个统一的、最终的用户自定义入口。无论你用的是哪个运行级别通常是3或5无论系统内置的服务启动顺序多么复杂你都可以把那些“杂七杂八”的、不属于任何标准服务包的自定义命令安心地放在这里执行。比如启动一个你自己编写的监控脚本、挂载一个特殊的网络存储NFS/Samba、或者为某个应用设置一个临时的内核参数。然而时代在变迁。Systemd以其并行启动、依赖关系管理、服务状态跟踪等强大特性逐渐取代了SysVinit成为绝大多数现代Linux发行版如RHEL/CentOS 7, Ubuntu 16.04, Debian 8的默认初始化系统。Systemd引入了*.service单元文件的概念启动过程变得更加模块化和可控。那么rc.local是不是就彻底消亡了并没有。出于对历史兼容性和用户习惯的尊重Systemd提供了一个rc-local.service单元专门用于在系统启动的后期执行/etc/rc.local脚本。这相当于为这个“老古董”穿上了一件Systemd的“新外衣”让它得以在新时代继续发挥作用。但需要注意的是在一些最新的、追求纯粹Systemd的发行版中这个服务可能默认是禁用甚至不安装的。因此我们今天讨论的配置流程实际上包含了两个层面在传统SysVinit系统上的原生用法以及在Systemd系统上的兼容性启用和配置。3. 配置 rc.local 的完整实操流程了解了背景我们进入实战环节。配置/etc/rc.local绝非简单地往文件里写几条命令那么简单它涉及到文件权限、执行环境、依赖顺序等多个细节。下面我们分步骤详解。3.1 环境检查与文件准备在动手之前首先要确认你的系统是否支持rc.local以及它以何种形式存在。检查文件是否存在ls -l /etc/rc.local如果文件不存在你需要创建它。在Systemd系统上更常见的路径可能是/etc/rc.d/rc.local这是一个指向/etc/rc.local的符号链接。无论哪个路径最终指向的是同一个文件。检查执行权限rc.local本质上是一个Shell脚本。因此它必须拥有可执行x权限否则系统无法运行它。# 查看当前权限 ls -l /etc/rc.local # 如果没有执行权限则添加 sudo chmod x /etc/rc.local这是最容易忽略的一步很多配置失败的原因就是忘了给文件加执行权限。检查Systemd的rc-local服务仅适用于Systemd系统systemctl status rc-local如果服务不存在你可能需要安装它在某些最小化安装的系统中。如果服务存在但为disabled或inactive则需要启用和启动它。3.2 编写 rc.local 脚本内容创建或编辑/etc/rc.local文件通常使用vim或nano编辑器。sudo vim /etc/rc.local文件内容有固定的格式要求。第一行必须是指定解释器的Shebang。虽然大多数系统默认使用bash但显式声明是一个好习惯也能避免兼容性问题。#!/bin/bash # 这是一个注释说明此文件的作用 # 此脚本将在所有其他初始化脚本之后执行。 # 示例1: 将一行文本写入日志文件用于调试和确认脚本已执行。 echo $(date): rc.local script executed. /var/log/rc.local.log # 示例2: 启动一个自定义的后台服务或脚本。 # 假设你有一个位于 /opt/myapp/start.sh 的启动脚本。 # 使用 将其放入后台执行避免阻塞rc.local。 /bin/bash /opt/myapp/start.sh # 示例3: 设置环境变量或内核参数临时性。 # 注意这里设置的环境变量仅对rc.local启动的进程及其子进程有效。 export MY_APP_HOME/opt/myapp # 修改内核参数例如提升本地端口范围 sysctl -w net.ipv4.ip_local_port_range1024 65535 # 示例4: 挂载网络文件系统。 # 确保网络服务如network或NetworkManager已经启动。在Systemd下可以通过After依赖确保。 mount -t nfs 192.168.1.100:/shared /mnt/nfs_share # 示例5: 调整网卡设置如设置混杂模式用于监控。 # ip link set eth0 promisc on # 脚本必须以退出状态码0结束表示成功。 exit 0关键要点与避坑指南Shebang不可少#!/bin/bash必须放在第一行。使用绝对路径在启动脚本中环境变量$PATH可能与你登录Shell中的不同。因此对于所有命令和要执行的脚本强烈建议使用绝对路径如/bin/bash,/usr/bin/systemctl,/opt/myapp/start.sh。这是避免“command not found”错误的最有效方法。后台执行如果你的命令或脚本是持续运行的服务比如一个Python Web应用务必在命令末尾加上符号使其在后台运行。否则rc.local会一直等待该命令结束导致系统启动过程卡住。依赖关系你的命令可能依赖于其他服务。例如挂载NFS需要网络就绪。在传统SysVinit中这靠运行级别顺序保证。在Systemd中rc-local.service默认在network-online.target等目标之后启动但并非绝对。如果遇到依赖问题可能需要自定义Systemd单元文件后文会讲。输出重定向将命令的输出包括错误信息重定向到日志文件是调试的黄金法则。像上面例子中 /var/log/rc.local.log这样操作可以让你在启动后查看发生了什么。exit 0脚本最后返回0向系统报告执行成功。如果脚本中途出错你可以返回非零值但这通常不会阻止系统完成启动不过可能会在系统日志中留下错误记录。3.3 在Systemd系统上启用并测试对于使用Systemd的系统配置完文件后还需要显式启用服务。启用并启动 rc-local 服务# 启用服务使其在每次启动时自动运行 sudo systemctl enable rc-local.service # 立即启动服务用于本次测试而不重启系统 sudo systemctl start rc-local.service # 检查服务状态查看是否运行成功有无报错 sudo systemctl status rc-local.service在status的输出中你应该看到active (exited)状态并且日志显示它已成功执行。查看执行日志 Systemd提供了强大的日志工具journalctl可以方便地查看rc-local服务的详细输出。# 查看 rc-local 服务的所有日志 sudo journalctl -u rc-local.service # 查看本次启动以来的日志 sudo journalctl -u rc-local.service -b # 实时跟踪日志在另一个终端执行测试时很有用 sudo journalctl -u rc-local.service -f通过日志你可以清晰地看到脚本中每条命令的执行结果以及任何可能的错误信息如“Permission denied”、“command not found”。3.4 验证配置效果配置完成后最可靠的验证方法是重启系统。因为有些环境变量或内核参数只有在完整的启动流程中才能被正确设置。重启后通过以下方式验证检查自定义日志查看你在脚本中指定的日志文件如/var/log/rc.local.log。检查进程使用ps aux | grep myapp查看你的自定义服务是否在运行。检查挂载点使用df -h或mount | grep nfs查看网络存储是否已挂载。检查系统日志使用journalctl -u rc-local或直接查看/var/log/messages、/var/log/syslog取决于发行版。4. 常见问题排查与深度解析即使按照流程操作你也可能会遇到问题。下面是一些典型故障及其排查思路。4.1 脚本未执行权限与服务状态症状重启后自定义的任务没有执行/var/log/rc.local.log文件没有创建或内容为空。排查步骤检查文件权限再次确认ls -l /etc/rc.local必须有x权限。检查Shebang用cat -A /etc/rc.local查看文件开头确保#!/bin/bash是文件的第一行并且行尾没有奇怪的符号如Windows换行符^M$。如果有使用dos2unix命令转换。检查Systemd服务状态systemctl status rc-local如果服务是inactive (dead)说明它从未运行。执行sudo systemctl start rc-local并再次查看状态和日志。如果状态显示失败重点看journalctl -xe或journalctl -u rc-local输出的错误信息。检查服务是否被屏蔽极少数情况下服务可能被mask彻底禁用。使用systemctl is-enabled rc-local检查如果返回masked需要用sudo systemctl unmask rc-local解除。4.2 命令执行失败路径与环境变量症状日志中显示 “/bin/bash: /opt/myapp/start.sh: No such file or directory” 或 “xxx: command not found”。根因分析这是rc.local配置中最常见的坑。脚本执行时的环境与用户登录后的Shell环境截然不同。$PATH变量非常精简通常只包含/bin、/sbin等少数目录。你的自定义脚本或命令如果不在这些目录下又没有使用绝对路径就会找不到。解决方案对所有命令使用绝对路径这是铁律。不要假设python、node、java这些命令在PATH里。用which python3找到它的绝对路径例如/usr/bin/python3。在脚本内设置PATH可以在rc.local文件的开头在Shebang之后显式设置需要的路径。#!/bin/bash export PATH/usr/local/bin:/usr/bin:/bin:/sbin:/usr/sbin # ... 其余命令为自定义脚本加可执行权限确保你调用的那个脚本如/opt/myapp/start.sh本身也有x权限。4.3 依赖顺序问题网络未就绪症状脚本中挂载NFS或访问网络资源的命令失败但手动执行同样的命令却成功。根因分析rc.local虽然设计为最后执行但在Systemd中rc-local.service的启动时机是相对固定的。它可能在某些网络服务还未完全进入“就绪”状态时就执行了。例如network.service可能只负责启动网卡而network-online.target才代表网络真正可用。解决方案修改Systemd服务单元的依赖关系。这是进阶操作但能从根本上解决问题。创建或编辑覆盖配置推荐方式不修改原始文件sudo mkdir -p /etc/systemd/system/rc-local.service.d sudo vim /etc/systemd/system/rc-local.service.d/override.conf在文件中添加以下内容确保在网络和远程文件系统挂载点就绪后再执行rc.local[Unit] # 增加依赖确保网络在线和远程文件系统就绪 Afternetwork-online.target remote-fs.target Wantsnetwork-online.target remote-fs.targetAfter定义启动顺序Wants表示一种弱依赖关系。重新加载Systemd配置并重启服务sudo systemctl daemon-reload sudo systemctl restart rc-local4.4 脚本阻塞启动过程症状系统启动时间异常漫长甚至卡住最后可能超时进入紧急模式。根因分析脚本中包含了长时间运行且没有放入后台的前台命令。rc.local会顺序执行其中的命令并等待每一个命令结束。如果一个命令比如一个交互式脚本或者一个本该是守护进程但错误地以前台模式运行的程序一直不结束rc.local就无法继续进而导致启动流程卡住。解决方案对守护进程使用如前文示例/bin/bash /opt/myapp/start.sh 。使用nohup对于需要脱离终端运行的脚本可以组合使用nohup和并将输出重定向到空设备或日志文件。nohup /usr/bin/python3 /opt/myapp/app.py /var/log/myapp.log 21 考虑改用Systemd服务单元如果一个程序需要作为常驻服务运行并且对启动、停止、重启、日志有更精细的管理需求那么为其创建一个专用的.service文件是更专业、更推荐的做法。rc.local更适合执行一次性的、简单的初始化任务。5. 现代最佳实践何时用 rc.local何时用 Systemd Service经过上面的分析你应该对rc.local的优劣有了清晰的认识。我们来做个总结和对比帮助你在实际工作中做出正确选择。继续使用/etc/rc.local的场景简单的一次性任务例如在启动时写入一个标志文件、删除某个临时目录、发送一条通知消息。遗留系统维护你管理的服务器仍然是CentOS 6或更早的版本SysVinit是唯一选择。快速原型与测试在开发环境中你想快速验证某个服务是否能在启动时跑起来用rc.local修改和测试非常快捷。跨发行版的简单兼容脚本如果你写的脚本需要在不同初始化系统的机器上运行在Systemd机器上启用rc-local在SysVinit机器上直接用可以保持脚本主体一致。升级为 Systemd Service Unit (.service文件) 的场景常驻守护进程你的应用需要像nginx、mysql一样作为后台服务持续运行并且需要systemctl start/stop/restart/status这样的标准管理接口。复杂的依赖关系服务A必须在服务B之后启动并且依赖于某个套接字或挂载点。Systemd的[Unit]节可以清晰地定义After,Requires,Wants等依赖。资源管理与安全控制你需要限制服务使用的CPU、内存CPUQuota,MemoryMax或者以特定用户/组身份运行User,Group或者设置Linux能力集、命名空间等。这些是rc.local无法提供的。自动重启与故障恢复你希望服务崩溃后能自动重启Restarton-failure这是生产环境服务的常见需求。集中化日志你希望服务的所有输出stdout/stderr都通过journalctl统一管理而不是自己维护日志文件。一个简单的抉择法则如果你的任务超过3行简单的Shell命令或者它需要长期运行、需要被管理、需要可靠的依赖保障那么请花20分钟为它编写一个Systemd服务单元文件。这会让你的运维生活更加轻松和规范。对于真正的一次性、简单的初始化任务rc.local依然是一个干净利落的工具。6. 从 rc.local 平滑迁移到 Systemd Service假设你有一个通过rc.local启动的Python应用现在决定将其迁移为标准的Systemd服务。这是一个典型的升级过程。原有/etc/rc.local中的内容#!/bin/bash /usr/bin/python3 /opt/myapp/app.py --port 8080 /var/log/myapp.log 21 迁移步骤创建Systemd服务单元文件sudo vim /etc/systemd/system/myapp.service编写服务文件内容[Unit] DescriptionMy Python Application # 明确声明依赖在网络就绪后启动 Afternetwork.target # 可以定义更复杂的依赖如数据库 # Afternetwork.target mysql.service [Service] # 指定执行命令和参数 ExecStart/usr/bin/python3 /opt/myapp/app.py --port 8080 # 指定工作目录 WorkingDirectory/opt/myapp # 以哪个用户身份运行更安全 Userappuser Groupappuser # 服务崩溃后自动重启 Restarton-failure # 重启间隔 RestartSec10s # 标准输出和错误输出重定向到系统日志 StandardOutputjournal StandardErrorjournal # 也可以重定向到文件 # StandardOutputfile:/var/log/myapp.log # StandardErrorfile:/var/log/myapp.log [Install] # 定义如何安装此服务multi-user.target对应运行级别3 WantedBymulti-user.target从 rc.local 中移除对应行编辑/etc/rc.local删除或注释掉启动该Python应用的那一行。启用并启动新服务# 重新加载Systemd配置 sudo systemctl daemon-reload # 启用开机自启 sudo systemctl enable myapp.service # 立即启动服务 sudo systemctl start myapp.service # 检查状态和日志 sudo systemctl status myapp.service sudo journalctl -u myapp.service -f完成以上步骤后你的应用就从一个“黑盒”脚本变成了一个可被Systemd全生命周期管理的标准服务。你可以方便地查看其状态、日志控制其启停并享受依赖管理和自动重启等高级特性。这个迁移过程正是Linux系统管理从“脚本化”走向“服务化”、“标准化”的缩影。理解/etc/rc.local正是为了在合适的时机优雅地超越它。

相关新闻

移动端高性能拖拽实现:从touchmove原理到实战优化

移动端高性能拖拽实现:从touchmove原理到实战优化

1. 项目概述:从点击到滑动的交互革命在移动端网页开发中,实现一个元素的平滑拖动效果,是提升用户体验的关键一环。这不仅仅是“点击”事件的简单延伸,而是涉及到触摸屏上一系列连续、精细手势的捕获与响应。我们常说的touchmove事…

2026/10/15 8:57:05 阅读更多 →
专业双语工资单制作指南:从核心字段解析到Excel自动化实操

专业双语工资单制作指南:从核心字段解析到Excel自动化实操

1. 项目概述:为什么我们需要一张“双语工资单”?在跨国企业、外资公司或者有外籍员工的团队里工作,每个月最让人头疼的环节之一,可能就是收到工资单的那一刻。对于中方员工,看到一堆英文缩写和术语,常常一头…

2026/10/14 17:34:03 阅读更多 →
Ant Design Vue表格性能优化:虚拟滚动原理与实战集成指南

Ant Design Vue表格性能优化:虚拟滚动原理与实战集成指南

1. 从“卡顿”到“丝滑”:为什么我们需要虚拟滚动最近在重构一个后台管理系统,遇到了一个非常典型的前端性能问题:一个用于展示用户操作日志的表格,当数据量超过500条时,页面就开始有明显的卡顿感,滚动起来…

2026/10/15 6:53:19 阅读更多 →

最新新闻

T3 Stack 全栈开发实战:类型安全架构从入门到避坑指南

T3 Stack 全栈开发实战:类型安全架构从入门到避坑指南

在前后端分离大行其道的今天,TypeScript 全栈方案已经不是什么新鲜词。但有一个技术组合,从 2022 年开始就在海外开发者圈子里持续霸榜,直到现在依然是很多团队做中大型项目的首选架构,就是 t3code 背后这套技术栈——更准确地说&…

2026/10/15 8:58:11 阅读更多 →
Spring无参构造器Bean实例化机制详解

Spring无参构造器Bean实例化机制详解

1. 无参构造器场景下的Spring Bean创建机制解析在Spring框架的核心实现中,createBean方法作为Bean实例化的关键入口,其构造器选择逻辑直接影响着依赖注入的行为模式。今天我们就来深入探讨Spring在无参构造器场景下的实例化策略,这是理解Spri…

2026/10/15 8:58:11 阅读更多 →
7件做了必定后悔的人生决策与预防策略

7件做了必定后悔的人生决策与预防策略

1. 项目概述"老王-7件事做了必定后悔"这个标题看似简单,却蕴含着丰富的人生经验总结。作为一个长期关注个人成长与决策优化的实践者,我发现在日常生活中确实存在一些看似平常但后果严重的决策陷阱。这些决策往往在当时显得合情合理&#xff0c…

2026/10/15 8:58:11 阅读更多 →
水波透射仿真:光学原理在海洋工程中的应用

水波透射仿真:光学原理在海洋工程中的应用

1. 项目背景与核心问题这个光学仿真项目研究的是水波在遇到多个垂直薄板时的透射行为。作为一名长期从事波动光学研究的工程师,我发现这类问题在海洋工程、声学屏障设计等领域有着广泛的应用价值。比如在设计防波堤时,我们需要精确预测波浪能量通过障碍物…

2026/10/15 8:58:11 阅读更多 →
Windows本地账户密码遗忘:安全重置全流程指南

Windows本地账户密码遗忘:安全重置全流程指南

1. 项目概述:当Windows登录界面变成一道锁,你手里的钥匙去哪儿了?“Windows系统遗忘密码怎么办”——这短短十个字,背后是数以百万计普通用户在清晨赶着开电脑写报告、深夜调试程序突然卡住、或是帮家里老人修电脑时最常遇到的窒息…

2026/10/15 8:58:11 阅读更多 →
膜反应器原理、应用与维护全解析

膜反应器原理、应用与维护全解析

1. 膜反应器概述膜反应器作为一种将反应与分离过程耦合的装置,在化工、生物、环境等领域已有超过50年的应用历史。我第一次接触这类设备是在2012年参与某制药废水处理项目时,当时使用的中空纤维膜组件至今仍在稳定运行。这种将化学反应与膜分离技术相结合…

2026/10/15 8:57:11 阅读更多 →

日新闻

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/14 3:30:28 阅读更多 →
影刀RPA新手教程:键盘模拟输入实战——输入文本与模拟按键的区别

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

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

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

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

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

2026/10/14 3:29:58 阅读更多 →

月新闻

我发现了一个新思路:用 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/14 7:53:34 阅读更多 →