type属性仅作用于当前ol元素,不继承也不穿透子列表,每个嵌套ol都必须显式声明自己的type值;子ol必须严格包裹在父级li内,否则dom结构断裂、编号重置。

type 属性只控制当前 ol,不继承也不穿透子列表
很多人以为给外层 ol type="A" 后,里面嵌套的 ol 会自动变成 type="1" 或按层级递进——这是错觉。浏览器根本不做这种“智能推导”,type 是纯局部属性,每个 ol 都得显式声明自己的编号类型。
常见错误现象:嵌套时漏写内层 type,结果所有子项都显示为数字 1、2、3,哪怕父级是 A.、B.;或者误以为 type="a" 在第二层会自动生效,实际它根本没被设置。
- 第一级必须写
type="A"(或"1"、"I"等) - 第二级必须单独写
type="1",不能省略 - 第三级必须单独写
type="a",哪怕它在type="1"的li里 - CSS 的
list-style-type可以覆盖type,但优先级低,且不解决语义问题
嵌套必须严格在 li 内部,不能并列放在 ol 外
这是最常踩的结构坑。HTML 规范要求:子 ol 或 ul 必须作为某个 li 的直接子元素,而不是和 li 平级放在父 ol 里。否则浏览器会自动闭合前一个 li,导致编号重置、层级断裂、可访问性工具读错顺序。
错误写法示例(看着像嵌套,实则非法):
<ol type="A"> <li>A. 主项</li> <ol type="1"><li>1. 子项</li></ol> <!-- ❌ 这个 ol 不在 li 里 --> </ol>
正确写法(子 ol 必须包裹在 li 内):
<ol type="A">
<li>A. 主项
<ol type="1">
<li>1. 子项</li>
<li>2. 子项</li>
</ol>
</li>
</ol>
start 和 value 的行为差异很关键
start 控制整个 ol 的起始编号,而 value 只作用于单个 li,且会影响后续项的自动计数——这点极易被忽略。
-
start="5":整组从 5 开始,后面是 6、7、8… -
<li value="10">…</li>:该项显示为 10,下一项自动变成 11(不是 1),再下一项是 12 - 如果混用:
<ol start="5"> <li value="8">…</li> <li>…</li> </ol>,第二项是 9,不是 6 -
reversed与start共存时,start指的是倒序后的第一个值,比如<ol reversed start="3"></ol>显示为 3、2、1
CSS list-style-type 能覆盖 type,但语义丢失
用 CSS 写 style="list-style-type: lower-roman;" 确实能让编号变样,但它只是视觉层替换,HTML 结构里仍无对应语义信息。这对屏幕阅读器、打印样式、搜索引擎解析都不友好。
更麻烦的是兼容性细节:
-
lower-alpha在旧版 Safari 中可能 fallback 到数字 -
upper-roman对大于 3999 的值不渲染(I~MMMCMXCIX 是极限) - 若同时写了
type="a"和list-style-type: upper-alpha,后者优先,但语义仍是小写字母 - 真正需要语义+样式双保障时,
type属性仍是首选,CSS 仅作微调补充
多级编号真正难的不是写法,而是每次嵌套前都要确认:这个 ol 是否被包在 li 里、它的 type 有没有显式声明、value 有没有意外干扰后续计数——这三个点漏掉任意一个,编号就大概率崩掉。
前端入门到VUE实战笔记:立即使用
在学习笔记中,你将探索 前端 的入门与实战技巧!











