嵌套有序列表必须严格遵循HTML父子关系,子ol必须直接嵌套在父li内;type和start属性仅作用于当前ol,不继承;复合编号需用CSS counters()实现。

嵌套有序列表能正常工作,前提是结构合法;浏览器不认“看起来像嵌套”的写法,只认严格符合 HTML 规范的父子关系。
ol 必须直接包裹子 ol,不能放在外面
常见错误是把两个 <ol> 并列写,比如先写一个 A. 的列表,再另起一个 <ol type="1"> 放在它后面。这样浏览器会把第二个 <ol> 当作全新列表,编号永远从 1 开始,而不是继承上一级的 B. 或 C.。
- ✅ 正确:子
<ol>必须是父级<li>的直接子内容,不能脱离<li> - ❌ 错误:
<ol type="A"></ol><ol type="1"></ol>—— 这是两个独立列表,毫无嵌套关系 - ⚠️ 注意:
<p>、<div>或空行不会“隐式包裹”子列表,它们会直接破坏嵌套语义
type 属性只控制本层编号样式,不传递给子层
type 属性(如 type="A"、type="1")只影响当前 <ol> 的编号类型,子 <ol> 必须显式声明自己的 type,否则默认用 type="1"。浏览器不会自动“推导”子层该用什么类型。
- 第一级用大写字母:
<ol type="A"> - 第二级必须手动写:
<ol type="1">(不能省略) - 第三级同理:
<ol type="a">,否则仍是 1.、2.、3. - 如果某级想跳过编号(比如只做容器),就别用
<ol>,改用<div>+ CSS
start 属性只对当前 ol 生效,不影响子 ol 起始值
start 属性(如 start="34")只设定当前 <ol> 的第一个编号值,子 <ol> 仍从 1 或 A 开始计数——它不会自动拼接成 34.1 或继承 34 作为前缀。
立即学习“前端免费学习笔记(深入)”;
- 想实现 34.1、34.2 这类复合编号,必须用 CSS
counters()函数,配合counter-reset和content - 单纯靠
start+ 嵌套<ol>只能做到:外层 34、35、36,内层各自从 1 开始 -
value属性可用于单个<li>强制指定编号(如<li value="34.1">),但不可用于整层自动递增
用 counters() 实现 2.1、2.1.1 这类带点分隔的编号
当需要跨层级拼接编号(如外层 start="2" → 内层显示 2.1、2.2),唯一可靠方式是放弃 type 和 start 的默认行为,改用 CSS 计数器接管全部逻辑。
- 关键:给外层
<ol>设置counter-reset: section,再用counter-increment: section控制递增 - 子层用
counters(section, ".")在::before中生成带点的前缀 - 必须配合
list-style: none关闭默认编号,否则会和伪元素冲突 - 示例片段:
ol { counter-reset: section; } ol li { counter-increment: section; } ol li::before { content: counters(section, ".") ". "; }
最容易被忽略的是:哪怕只是加了一个 <div> 包裹子 <ol>,或者在 <li> 里多写了个 <p> 标签,都可能让子 <ol> 脱离语义嵌套路径,导致计数器重置或样式失效。结构比样式更优先——先确保 DOM 层级正确,再谈编号怎么显示。



















