1. Atlas 300V到底是张什么卡24G显存的真实含义最近后台好几个朋友都在问同一个问题Atlas 300V尤其是Atlas 300V Pro的24G版本到底是不是一张运算加速卡能不能拿来跑YOLO。这问题看起来简单但背后混杂了太多信息差——有人把它当成GPU的平替有人以为它跟游戏显卡一样插上就能用还有人拿它跟3090、A10比算力。我先给个明确结论Atlas 300V是一张标准的AI推理加速卡不是训练卡更不是图形卡它的核心定位是把训练好的模型高效跑起来而24G指的是板载内存容量对应的是能装下多大的模型、跑多大的batch和你理解的GPU显存有本质区别。先说清楚运算加速卡这个概念。运算加速卡是个宽泛说法包含GPU、FPGA、ASIC等各种形态。Atlas 300V属于ASIC路线里的AI专用芯片内部集成的是昇腾AI Core专门为神经网络推理场景做了大量硬化设计。它和GPU的关键差异在于GPU是通用并行计算架构什么都能算但什么都不是最优昇腾AI Core是专用数据流架构对卷积、矩阵乘这类算子做了指令级优化同样的功耗和面积下推理吞吐更高。代价就是通用性差——不能拿来跑CUDA程序不能玩CUDA生态里那套现成库所有模型都得经过工具链转换成昇腾的离线模型格式才行。那24G具体有多大价值Atlas 300V Pro 24G版本板载24GB LPDDR4X内存带宽在204GB/s左右。这个数字放在当下看足够装下参数量在10亿以内的主流视觉模型。拿YOLO家族来说YOLOv5s的权重文件才14MB左右转成OM模型后也就30-40MB跑batch 1时显存占用不超过2GB。就算上YOLOv8x模型转出来也就200多MB24G内存完全是小菜一碟。真正吃内存的场景是跑大batch或者多路视频流并发。比如你要做16路甚至32路1080P视频流的实时检测每路一个推理线程batch叠上去内存占用就会几何级增长这时候24G版本的优势就体现出来了——不用频繁做内存换入换出喂数据更从容。从板卡形态上说Atlas 300V是一张标准PCIe半高半长卡功耗75W左右不需要外接供电插在普通x86服务器的PCIe x16槽位上就能用散热要求也不高。这一点对很多做边缘计算、私有化部署的团队特别友好——不用买动辄几千瓦电源的工作站一台普通的2U服务器就能带两张甚至三张卡。但这也会带来一个认知误区很多人以为它和显卡一样插上就能用实际上它需要完整的驱动、固件和CANN工具链配合初始化流程比GPU复杂得多。这个坑后面专门讲。对比维度Atlas 300V Pro 24G常见GPU推理卡如RTX 3090芯片架构昇腾AI Core数据流架构CUDA通用并行架构板载内存24GB LPDDR4X204GB/s24GB GDDR6X936GB/s典型功耗75W350W模型格式OM离线模型需转换TensorRT Engine / ONNX Runtime训练支持不支持支持但3090也非训练最优视频解码支持硬件解码DVPP需另配解码卡或CPU解码生态成熟度昇腾社区相对垂直CUDA生态资源丰富功耗只有3090的五分之一内存带宽也差一个量级但推理场景下它的实际吞吐并不差——因为推理任务高度规律化专用架构的效率优势能抵消一部分带宽劣势。这就是为什么华为敢把它定位成AI推理加速卡而不是低配GPU。2. 部署YOLO前的环境准备最容易翻车的环节其实是驱动和固件不少人拿到Atlas 300V之后第一件事就是装驱动然后发现官方文档写得云里雾里装完系统起不来或者npu-smi根本看不到卡。我可以负责任地说这个环节的翻车率比后续跑YOLO高得多。它不像装NVIDIA驱动那样apt install nvidia-driver-xxx就完事昇腾的软件栈是分层的底层是HDK包含驱动和固件往上是CANN工具包再往上才是推理引擎MindSpore Lite、ACL等。这三层必须严格匹配版本否则就是各种诡异报错。2.1 版本匹配是第一道生死关在动手之前先把服务器操作系统确定下来。Atlas 300V官方支持的操作系统是这几个Ubuntu 18.04/20.04 x86_64和aarch64、CentOS 7.6/7.9、openEuler 20.03/22.03、以及统信UOS等国产系统。我个人的建议是能用Ubuntu 20.04就用Ubuntu 20.04别问为什么问就是社区踩坑案例最少、第三方兼容性最好。CentOS虽然也支持但很多依赖包要自己手动装搞起来心累。系统定下来之后去昇腾社区下载对应版本的软件包。这里有个关键点你下载的不是一个包而是两个——驱动固件包Ascend-hdk-xxx.run和CANN工具包Ascend-cann-toolkit_xxx.run。这两个包的版本号要对上。比如CANN 6.3.RC2配套的HDK版本就是6.3.RC2系列。版本不匹配的典型症状是驱动能加载但npu-smi看不到板卡信息或者运行样例时报runtime init failed。装驱动和固件的命令其实不复杂# 以root身份安装HDK包包含驱动和固件 ./Ascend-hdk-*.run --full --quiet # 安装完成后检查是否识别到NPU设备 npu-smi info执行完这个如果能看到Device信息显示芯片温度、内存占用、HBM频率这些字段说明硬件识别成功了。如果npu-smi提示No device优先检查两件事一是服务器BIOS里有没有开启Above 4G Decoding和Resizable BAR二是不是插在了PCIe x16槽位上有些主板的x4槽虽然物理上能插进去但带宽不够会导致初始化失败。2.2 CANN工具包安装与环境变量配置CANN是昇腾计算架构的全称Compute Architecture for Neural Networks它相当于昇腾的CUDA Toolkit。CANN工具包里面包含算子库、图编译引擎就是后面要用的ATC工具、运行时AscendCL以及各种调试工具。# 安装CANN toolkit注意要用非root用户执行安装 # 建议先创建用户并赋予权限 ./Ascend-cann-toolkit_*.run --install --quiet # 安装后必须source环境变量脚本 source /usr/local/Ascend/ascend-toolkit/set_env.sh这里有个最容易踩的坑很多人把CANN装在了root用户下然后用普通用户跑推理任务结果权限不够报一堆莫名奇妙的错。昇腾官方要求CANN安装目录属主必须是非root业务用户驱动和固件则可以root安装。正确的做法是先创建业务用户比如ascend_user然后把CANN以这个用户的身份安装。另外环境变量脚本每次开新终端都要source一遍要么把它写进.bashrc要么写进项目的启动脚本里。check# 确认环境变量生效 python -c from ctypes import cdll; cdll.LoadLibrary(libruntime.so); print(runtime OK)如果这一步顺利通过恭喜你的Atlas 300V已经具备了跑推理的基本条件。2.3 Python环境和第三方依赖YOLO模型转换和推理离不开Python。建议直接装Anaconda或者MinicondaPython版本选3.7或3.8。CANN对Python版本有严格的兼容性要求3.9以上在某些版本里会出现接口不兼容的情况。后续要装的依赖大致是这些onnx、numpy、opencv-python、protobuf、cffi、pyyaml。用pip一次性装好pip install onnx1.12.0 numpy opencv-python protobuf3.20.0 cffi pyyaml版本别太激进。我见过有人装了onnx 1.14结果转换时算子解析直接崩掉折腾了一下午才发现是protobuf和onnx版本冲突。昇腾的生态不像PyTorch那样天天迭代它的工具链是跟着CANN版本走的保守依赖永远比追新安全。3. YOLO模型转换全流程从PyTorch权重到OM离线模型环境准备完毕之后就到了整个部署链路的核心环节——把PyTorch训练好的YOLO模型转换成昇腾推理引擎能识别的OM格式。这个环节不理解原理的人会觉得是一堆黑魔法理解了之后就发现不过如此ATCAscend Tensor Compiler工具就是昇腾版编译器输入是ONNX模型输出是经过算子在离线预编译和内存静态编排的OM模型运行时不再需要逐算子解析直接按编译好的执行流跑。3.1 ONNX导出是转换质量的源头无论你用的是YOLOv5还是YOLOv8第一步都是把PyTorch权重导出成ONNX。YOLOv5的导出命令python export.py --weights yolov5s.pt --include onnx --opset 11 --simplifyYOLOv8的导出命令yolo export modelyolov8s.pt formatonnx opset12 simplifyTrue这里有个关键细节opset版本别太高。YOLOv8默认会用opset 17甚至更高但昇腾ATC目前对高版本opset的算子支持不够完整建议锁定在11-13这个区间。别问我为什么问就是昇腾算子适配的速度永远追不上ONNX社区的更新速度这是所有非GPU加速卡的共同痛点。导出的ONNX里YOLOv5的输出是三个特征图P3、P4、P5shape分别是[1, 255, 80, 80]、[1, 255, 40, 40]、[1, 255, 20, 20]80类的情况下255 3 × (5 80)。YOLOv8则是一个大输出[1, 84, 8400]里面同时包含分类分支和回归分支。这个差异会影响后处理的写法后面细说。3.2 AIPP配置文件把预处理塞进硬件里ONNX模型转换前需要准备一个AIPPAI Preprocessing配置文件。AIPP的作用是把图像缩放、减均值、除以标准差、RGB通道顺序转换这些预处理操作下放到硬件模块执行而不是在CPU/GPU上跑OpenCV那套逻辑。这样做的收益有两个一是推理线程不需要等待预处理完成整体延迟降低二是预处理卸载后CPU占用率下降多路并发时能塞更多路。YOLOv5的AIPP配置示例aipp_op { aipp_mode: static input_format: RGB_C mean: 0.0 mean: 0.0 mean: 0.0 min_chn_0: 0.00392156862745098 min_chn_1: 0.00392156862745098 min_chn_2: 0.00392156862745098 var_reci_chn_0: 1.0 var_reci_chn_1: 1.0 var_reci_chn_2: 1.0 crop_params { crop_mode: 2 width: 640 height: 640 } }几个字段的意思说一下。input_format: RGB_C表示输入图片是RGB三通道连续排布如果你的图片是OpenCV读的那应该是BGR_C。min_chn_0填的是1/255等价于把像素值从0-255归一化到0-1。crop_params里的crop_mode: 2表示中心裁剪加缩放——YOLO训练时用的就是letterbox预处理即保持宽高比缩放到640x640多余部分用灰色填充。AIPP模式下的letterbox实现直接把这块逻辑固化到硬件里Python端只需要读图和resize就够了。3.3 ATC命令转换与排查技巧准备好ONNX模型和AIPP配置后执行转换指令。以YOLOv5s为例atc --modelyolov5s.onnx \ --framework5 \ --outputyolov5s_om \ --soc_versionAscend310P3 \ --input_shapeimages:1,3,640,640 \ --insert_op_confaipp.cfg \ --output_typeFP32 \ --input_formatNCHW--soc_version这个参数非常关键必须和你手上的芯片型号对应。Atlas 300V对应的Soc型号是Ascend310P系列具体是310P3还是310P4用npu-smi info查看chip type一栏就能确认。填错了AIPP和算子优化策略都会走错分支即使转换成功推理结果也可能轻微异常比如边框偏了半个像素。转换成功率不是100%尤其是新版本YOLO。遇到的报错类型大致分三种算子不支持报Unsupported op XXX。解决办法是先--insert_op_conf看看能否用AIPP替代不能的话就得改ONNX图结构把不支持的算子用等价算子替换。YOLOv8的DFL层里有个MatMul算子早期CANN版本不支持需要手动拆开。维度推导失败报InferShape failed。通常是动态shape引发的把--input_shape里的动态维度改成固定值比如把-1改成1。精度异常转换成功但推理结果全错。优先排查AIPP配置里的通道顺序和归一化是否和训练时一致。YOLOv5用RGB还是BGR训练预处理里就填什么这个最容易忽视。转换成功的标志是生成.om文件和一段日志日志里会显示算子编译耗时和最终模型大小。如果生成的OM模型明显偏大比如100MB以上说明图优化可能没生效回头检查有没有加--optimize_levelO2。4. 推理代码落地的两条路线MindSpore Lite与ACL接口怎么选模型转换完成接下来就是写推理代码。昇腾生态里有两个主流选择MindSpore Lite推理框架和ACLAscendCL底层接口。对大多数人来说直接选MindSpore Lite就对了只有需要极致的自定义优化时才碰ACL。4.1 MindSpore Lite类似ONNX Runtime的使用体验MindSpore Lite提供了Python接口上手成本最低。首先是安装配套的Python包pip install mindspore-lite2.1.0推理代码的核心逻辑分四步加载模型、创建推理上下文、设置输入数据、执行推理。一个最小可用的YOLOv5推理脚本骨架import cv2 import numpy as np import mindspore_lite as mslite # 创建推理上下文指定使用昇腾NPU context mslite.Context() context.ascend.device_id 0 context.ascend.provider ge # 加载OM模型 model mslite.Model() model.build_from_file(yolov5s_om.om, mslite.ModelType.MINDIR, context) # 读取图像并做缩放 img cv2.imread(test.jpg) img_resized cv2.resize(img, (640, 640)) # 构建输入张量 input_tensor mslite.Tensor() input_tensor.set_data_from_numpy(img_resized.astype(np.float32) / 255.0) inputs [input_tensor] # 推理 outputs model.predict(inputs) # 拿到输出特征图数据 out0 outputs[0].get_data_to_numpy() # [1, 255, 80, 80] out1 outputs[1].get_data_to_numpy() # [1, 255, 40, 40] out2 outputs[2].get_data_to_numpy() # [1, 255, 20, 20]这段代码跑通之后你就已经完成了一次完整的NPU推理。第一次跑的时候可能有点慢因为NPU在初始化设备上下文之后的推理会进入稳定状态。4.2 后处理跨平台部署真正的工作量所在YOLO系列之所以在实际工程里比分类模型麻烦就是因为它有一个绕不开的后处理链路——解码、置信度过滤、NMS。这部分代码在GPU上跑和NPU上跑没有本质区别但有几个细节决定了最终识别效果。YOLOv5后处理的核心是解码三个特征图。标准的解码流程是先用sigmoid把网络输出映射到[0,1]区间然后配合预设的anchor网格还原出边界框坐标。因为输出维度是[1, 255, 80, 80]255拆开是3个anchor乘以854个坐标1个置信度80个类别先做一次transpose把通道维度换到最后一维然后逐像素解析。YOLOv8则完全不同。它的输出是[1, 84, 8400]84拆开是4个回归参数加80个类别概率。回归参数不是直接给边界框坐标的而是DFL解码后得到的4个距离值。要知道YOLOv8没有anchor它是anchor-free的后处理和YOLOv5对不上。这里分享一个经验如果你对后处理代码不熟悉优先参考ultralytics官方仓库里的非加速版本实现先把输出输出通道数搞清楚再动手写循环。很多人在这一步浪费了两三天就是因为没搞懂YOLOv8的DFL层输出是什么意思。NMS部分要注意NPU上跑NMS不能直接用PyTorch的torchvision.ops.nms因为此时你手里的数据是numpy数组。最简单的方式是用OpenCV的cv2.dnn.NMSBoxes或者自己写几十行代码做非极大值抑制。实测下来一张1080P图有几千个候选框时Python版NMS耗时十几毫秒虽然比NPU推理本身慢但在大多数业务场景里是可以接受的。4.3 多路视频流的架构设计如果你做的是视频流实时检测单个图像推理脚本远远不够。Atlas 300V真正的主场是多路并发——一张24G的卡同时跑16路甚至32路1080P视频流每路25FPS这是它相对GPU卡的一个巨大优势。多路并发的基本架构是生产者-消费者模型。视频流解复用可以用FFmpeg也可以直接用昇腾的DVPP硬件解码得到图像帧放进队列一组推理线程从队列取图送进NPU推理后处理线程拿到推理结果后做业务逻辑。队列长度、线程数、batch大小三个参数需要反复调优。我的经验值是batch 1时YOLOv5s在Atlas 300V上的单帧推理耗时大约在10-15毫秒取决于CANN版本和图优化程度理论单卡能跑到60-80FPS的吞吐。但实际部署时不要跑满留20-30%的余量因为视频流本身的起播、关键帧切换、网络抖动都会导致瞬时峰值。跑满的代价是偶发丢帧和延迟抖动这两件事在监控类项目里比吞吐量更致命。5. 性能调优与踩坑实录AIPP、内存复用、batch策略部署上去能跑只是第一步跑得好才是重点。这一章讲几个我在实际项目中反复踩坑后总结出来的调优经验每一条都是真金白银换来的。5.1 显存复用别让内存碎片拖垮多路并发Atlas 300V的内存管理和CUDA不同。CUDA有成熟的内存池机制PyTorch/ONNX Runtime会自动做缓存复用昇腾的ACL也提供内存池但需要显式配置。你如果在多路场景下不配置内存复用很可能会遇到越跑越卡、最后崩掉的诡异问题——每路推理都申请独立内存累积下来就是内存碎片和泄漏。MindSpore Lite可以设置context.ascend.arena_mode和arena_sizecontext.ascend.arena_mode mslite.ArenaMode.COMPUTE context.ascend.arena_size 8 * 1024 # 单位MB预分配8GB显存池为每个推理线程创建独立的Model实例但让它们共享同一个上下文和显存池——这样多路并发时的显存占用会稳定在一个平台期不会随路数线性增长。5.2 输入尺寸与内存带宽的平衡YOLO模型有个有趣的特点输入分辨率越高对IO带宽的消耗越大。用640x640的输入跑YOLOv5s第一层卷积的输入特征图是[1, 3, 640, 640]单张图就接近5MB的数据量乘以24路每秒25帧带宽压力立刻上来了。Atlas 300V的204GB/s看起来不小但这是理论峰值实际可用带宽要打对折。所以优先考虑用416x416甚至320x320的输入尺寸。对于监控场景的远距离目标416x416的精度损失通常只有2-3个百分点但吞吐能提升接近一倍。如果你的场景对精度要求苛刻可以保留640x640但把batch降到1并把多路并发数减小到8-12路。这个取舍没有银弹完全取决于业务对延迟和精度的具体需求。5.3 常见报错与排查速查表最后整理一份我遇到最多的报错及对应解法给各位省点排查时间。报错信息原因分析解决方案300301 Runtime inner error显存分配失败或内存池耗尽降低batch或并发路数检查是否存在显存泄漏A30001: Device not found驱动和CANN版本不匹配重新核对HDK与CANN版本号确保一一对应EZ3002: Init stream failed设备上下文初始化失败检查是否有其他进程占用NPU执行npu-smi info查看状态Unsupported op: XXX模型算子超出CANN支持范围更换opset版本、替换等价算子或升级CANN版本InferShape fail输入shape含动态维度固定输入shape后再转换Output shape mismatchAIPP裁剪和模型输入不一致核对AIPP配置的width/height与模型输入尺寸我再额外提醒一个坑Atlas 300V的驱动卸载时系统会把npu的内核模块一起卸载如果不重启系统npu-smi会一直处于semi-状态。所以在升级驱动或固件后务必重启一次服务器再进入正常使用流程。很多人改了驱动不重启排查了半天找不出问题其实只是内核模块没重新加载。6. 从一张卡到一套系统的最后一公里Atlas 300V跑通YOLO只是起点。这张卡真正的价值是在多路并发场景下的稳定输出而如何把单卡能力封装成一个对内可维护、对外可扩展的推理服务可能是后续更花时间的事情。常见的做法是用FastAPI包一层HTTP接口内部走多进程队列或者用gRPC做流式通信。接口层的设计口径上我始终建议把AIPP预处理和后处理逻辑全部收敛到服务内部外部只传入原始图像或视频流地址拿到的就是标准化的检测结果。这样不管是接视频监控平台还是接业务系统都不会被硬件工具链污染。我自己最认可的一个部署方式是Atlas 300V作为边缘节点跑YOLOv5s模型做实时检测结果通过MQTT推到上层业务平台。这个组合在成本、功耗、实时性三个维度上达到了一个比较舒服的平衡点。如果你也在评估边缘侧的目标检测方案也可以按这个思路先跑通POC——一张卡、一个YOLO模型、一台普通服务器就是一套完整的最小可行系统。配置和代码都跑通之后最后再分享一个细节CANN和MindSpore Lite这层工具链的版本升级一定要克制。昇腾社区有一个特点——版本之间兼容性不够平滑升级CANN大版本经常意味着重新转一遍所有OM模型这个工作量在模型多的时候非常痛苦。我的习惯是有重大性能或算子需求时才升级否则就停在稳定版本上把时间花在业务优化上。毕竟对我们做工程的人来说稳定跑一年的方案永远比最新但是没人验证过的方案值钱。
企业数字化 ERP 产品动态
相关推荐
安全审计实战指南:从威胁建模到漏洞修复的核心方法论与工具链 干安全审计这行久了,我越来越觉得它是一门被低估的手艺。很多人以为“security-audit-skill”就是拿工具扫一遍、出个报告、贴几个漏洞截图,然后拿着报告找开发改一改就完事。说实话,这种认知不仅低估了审计的复杂度,也浪费了它真… · 2026/9/25 8:47:40
无码间串扰的基带传输:高速数字链路的工程落地指南 简介:本资源是一份面向通信工程专业本科生及考研复习者的《无码间串扰的基带传输特性》核心知识点精讲文档,系统梳理数字基带传输中消除码间串扰的关键理论与设计方法。内容涵盖奈奎斯特第一准则的数学推导与物理意义、理想低通与升余弦滚降传输特性的对… · 2026/9/25 8:47:34
基于Go自研DNS调度系统Ax调度:从原理到代码实战 我正在负责一个对外提供解析服务的项目,域名量不大,但客户分布在全国各地,运营商也杂。早先用的是传统DNS解析方式,A记录直接配置,结果经常收到客户反馈:北方用户访问慢、某个运营商全网超时、半夜现网流量… · 2026/9/25 8:47:27
Atlas 300V 24G部署YOLO实战:从推理加速卡选型到模型转换调优 最近后台有不少人问我同一个问题:Atlas 300V 24G 到底算不算运算加速卡?能不能拿来部署 YOLO?正好我手上这套视频目标检测项目用的就是 Atlas 300V 系列,模型从 PyTorch 的 YOLOv8 转成 CANN 的离线模型再上卡推理,整个… · 2026/9/25 9:56:47
Atlas 300V 24G运算加速卡实战:YOLO部署全流程与调优 你可能已经发现,只要一搜“atlas”,出来的结果五花八门——有数据库中间件、有地图应用、还有一堆AI加速卡。但在“atlas部署yolo”和“atlas 300v 24g”这两个关键词组合出现时,事情就清晰了:大家问的基本是同一类东西࿰… · 2026/9/25 9:56:41
辽宁灯杆特色装饰制造厂家避坑挑选指南,韩式风灯杆装饰生产厂家筛选名录 辽宁灯杆特色装饰制造厂家避坑挑选指南选择靠谱的灯杆装饰生产厂家,是市政道路、文旅景区、商业街区亮化项目落地的核心前提。辽宁嘉上灯具制造有限公司作为扎根沈阳的户外亮化专精厂家,深耕东北道路节日亮化赛道9年,主营LED灯笼、LED中国结、… · 2026/9/25 9:56:23
BrowserSkill 完整指南:AI Agent 浏览器操作复用登录态,工作不被打断 BrowserSkill 完整指南:AI Agent 浏览器操作复用登录态,工作不被打断 【免费下载链接】BrowserSkill Let AI agents use your real, logged-in browser without interrupting your work. CLI extension for browser automation across any shell-capabl… · 2026/9/25 9:56:23
新疆靠谱的气动阀门厂家筛选名录:源头生产厂家实力盘点 在新疆能源工程领域,管道阀门的适配性直接决定整个管网系统的运行稳定性,尤其是对安全性能要求极高的气动阀门,筛选靠谱厂家从来不是一件小事。不同于通用款阀门,气动阀门多用于易燃易爆的油气、化工、燃气工况,对产品… · 2026/9/25 9:56:23
南京靠谱的野山参粉定制工厂有哪些?无尘加工实力与用户口碑深度解析 南京靠谱的野山参粉定制工厂有哪些?无尘加工实力与用户口碑深度解析
导语南京山品汇健康生物技术有限公司依托东北桓仁核心产区的原生野山参资源,专注国标真野山参甄选加工与定制服务,打造可溯源、高年份的野山参粉产品,为各类客户提供保真可… · 2026/9/25 9:56:16
创维E900V22D刷机全攻略:S905L3SB芯片兼容性解析与救砖实战 /* MD / 富文本中的 .toc(含博客园搬家等嵌套结构);.toc-box 在侧栏,不受影响 */#content_views .toc,/* 编辑器常在目录前后插入空 p(:empty 仍占 20px),一并去掉避免顶空隙 */#content_views.markdown_views > p:empty:has(+ .toc),#content_views.markdown_views … · 2026/9/25 1:00:31
MQTT协议原理与Broker服务器搭建实战:从Mosquitto到EMQX /* MD / 富文本中的 .toc(含博客园搬家等嵌套结构);.toc-box 在侧栏,不受影响 */#content_views .toc,/* 编辑器常在目录前后插入空 p(:empty 仍占 20px),一并去掉避免顶空隙 */#content_views.markdown_views > p:empty:has(+ .toc),#content_views.markdown_views … · 2026/9/25 1:00:37