less守卫必须紧接mixin定义括号后、大括号前,类型匹配需严格,多分支按顺序匹配且需兜底,守卫仅在编译期生效,不响应运行时状态。

守卫表达式写在错误位置导致完全不解析
Less 的 when 必须紧接在 mixin 定义括号之后、大括号之前,且不能嵌套在选择器或规则块内部。写错位置会导致编译器直接忽略守卫,当作无守卫 mixin 处理。
-
.btn() when (@size = "large") { ... }✅ 正确:守卫是 mixin 声明的一部分 -
.btn() { .inner() when (@size = "large") { ... } }❌ 错误:守卫在嵌套规则里,编译器不识别 -
.btn when (@size = "large") { ... }❌ 错误:漏了括号,.btn被当选择器而非 mixin 名
常见现象是守卫“像没写一样”,所有分支都输出,或只输出无守卫版本——先检查语法结构是否合法。
变量类型或值不匹配导致守卫恒为 false
Less 守卫比较严格区分类型和字面量。数字 10 和字符串 "10" 不相等;未加引号的 large 被当作变量名,若未定义就报 Variable @large is undefined。
- 写
@size: "large"; .btn() when (@size = "large")✅ 字符串对字符串 - 写
@size: large; .btn() when (@size = large)✅ 且前提是@size: large;已声明为关键字 - 写
@size: 12px; .btn() when (@size > 10)❌ 单位不一致,12px > 10是非法操作,应写(@size / 1px) > 10 - 用
iskeyword(@size)或isstring(@size)显式判断类型再分支,比盲目比较更可靠
多个 when 分支顺序不当造成前置守卫“吃掉”后续逻辑
Less 按定义顺序逐个匹配守卫,遇到第一个为 true 的就停止,不会继续检查后面的分支。这不像 JS 的 if-else 链可设默认 fallback,而是纯靠书写顺序控制优先级。
- 把宽泛条件(如
when (@theme))放在前面,会遮挡后面更具体的when (@theme = "dark") and (@mode = "compact") - 否定守卫如
when not (@theme = "light")应放在最后,否则它会匹配所有非 light 主题,让其他分支失效 - 必须提供一个无守卫的兜底 mixin,否则当所有守卫都不匹配时,整个规则不输出 CSS —— 这是静默失败,DevTools 里根本看不到该样式
守卫里混入运行时概念导致逻辑失效
when 是编译期守卫,只响应 Less 变量和函数计算结果,对 CSS 伪类、媒体查询、DOM 状态、JS 变量完全无感。误以为它能响应 :hover 或 @media (max-width: 768px) 是最典型的误解。
-
.btn() when (@size = "large") and (hover) { ... }❌hover不是 Less 变量,编译报错 -
.btn() when (@size = "large") { &:hover { ... } }✅ 可行,但&:hover是静态生成,不是守卫触发的动态行为 - 需要响应用户交互?用 class 切换 + CSS 类名组合,或 JS 控制类名,别指望
when
真正容易被忽略的是:守卫不参与 CSS 层叠权重计算,也不影响浏览器渲染时机。它只是决定“这一段 CSS 规则要不要生成”。一旦编译完成,就和普通 CSS 无异——没有魔法,只有确定性输出。
前端入门到VUE实战笔记:立即使用
在学习笔记中,你将探索 前端 的入门与实战技巧!











