`
---
# 三、命名多单词规则
- 块、元素、修饰符内部多个单词:用**单横线 `-`**
- 块与元素分隔:**双下划线 `__`**
- (块|元素)与修饰符分隔:**双横线 `--`**
示例:
```
.user-profile 块:用户资料
.user-profile__avatar 元素:用户资料的头像
.user-profile__avatar--large 修饰:大尺寸头像
```
---
# 四、BEM常见误区
### 1. ❌不要无限嵌套`__`
```
//错误
.card__header__title{}
//正确
.card__header-title{}
```
### 2. ❌修饰符不能单独使用
修饰符只是追加样式,基础类必须保留。
### 3. ❌不要把页面结构当块
块是可复用组件,不是页面布局容器;页面布局可以单独写布局类。
### 4. ❌不要 DOM 结构和 BEM 强行绑定
BEM是组件语义,不是html层级;DOM嵌套深不代表要多加`__`。
### 5. ✅允许块嵌套另一个块
一个块内部可以放另一个独立块:
```html
```
如果这个search-form只是card内部专属、不能单独拿出去用,才写成`card__search-form`。
---
# 五、BEM的优缺点
### ✅优点
1. **语义化**:看类名就知道属于哪个组件,是什么角色,什么状态
2. **避免选择器冲突**,减少权重滥用,少用`!important`
3. 组件化,方便复制、迁移、复用组件
4. 便于团队协作,统一命名习惯,大项目维护友好
5. 和css module、scss配合非常适配
### ❌缺点
1. 类名很长,html标签会比较臃肿
2. 新手容易滥用`__`,过度嵌套命名
3. 需要严格遵守约定,团队要统一认知
# 六、DOM多层嵌套的写法
**HTML嵌套,跟BEM的`__`没关系!DOM嵌套 ≠ BEM嵌套,**`__`只能出现一次,不能写 `a__b__c`。
### 场景举例:DOM是三层嵌套
```html
```
❌错误写法(跟着DOM层级多加`__`)
```css
.card__head__title {} /*禁止双下划线叠加*/
```
✅正确:元素内部多单词用**单横线 `-`**
```html
```
```css
.card {}
.card__head {}
.card__head-title {} /* 一次__,后面用单横线 */
```
规则:`block__xxx-yyy`
- `__`:**仅1次**,分割块和第一级子元素
- 后面再细分,全部用普通 `-`,不要再加 `__`
---
### 案例2:更深DOM层级例子
HTML DOM结构(4层标签嵌套)
```html
```
CSS:
```css
/* block */
.modal {}
/* element,__只写一次,后面全部单横线 */
.modal__wrapper {}
.modal__wrapper-inner {}
.modal__wrapper-inner-content {}
.modal__wrapper-inner-title {}
```
**注意:** `modal__wrapper-inner-title` 不要写成 `modal__wrapper-inner-content-title`,**不需要把完整 DOM 路径全部拼接进类名**。类名超长,DOM 改一层,类名就要大改,维护灾难。
## 两种嵌套区分:「组件内部子元素」vs「嵌入另一个独立组件」
### 情况A:这个子模块只属于父块,拿出去不能用 → 用 `block__xxx-yyy`
```html
```
```css
.card {}
.card__footer {}
.card__footer-btn {}
```
### 情况B:里面是完全独立组件,可以拿出来到处复用 → **不要再加父块前缀,直接用自己的block**
❌不要写成 `.card__button`
✅直接写 `.button`
```html
```
```css
.card {}
.card__footer {}
.button {}
.button--primary {}
```
---
## ❌禁止操作汇总
1. 禁止多个`__`
```css
/* 错 */
.modal__a__b__c {}
/* 对 */
.modal__a-b-c {}
```
2. 不要用后代选择器去规避BEM(很多人图省事这么写,BEM不推荐)
```css
/* 不推荐,增加权重,破坏BEM扁平思想 */
.modal .modal__wrapper .title {}
/* 推荐:直接给标签挂类名 */
.modal__wrapper-title {}
```
BEM思想:**尽量给需要样式的DOM节点直接挂class,少依赖DOM层级关系选择样式**,就算HTML嵌套很深,每个需要样式的节点直接写完整BEM类名。
# 七、好处
解决大型项目 CSS 混乱、选择器权重打架、命名冲突、组件不好复用的问题。
1. 类名自带语义,看 class 就知道是什么
2. **彻底减少样式冲突**
3. CSS 选择器扁平,权重可控,少用 `!important`
4. 组件可复制、迁移复用
5. HTML 结构改变,CSS 不容易坏
6. 团队协作统一,降低沟通成本
7. 和 CSS Module / Vue scoped / Tailwind 之外的传统项目适配很好
# 总结
- 块内单词单横杠,块元之间双下划;
- 状态变体双横杠,修饰永远不独行;
- 下划线只准一次,独立块不要套进元素。
- HTML随便嵌套几层,BEM的`__`最多出现一次;
- 后续细分全部 `-`;
- 内部如果是独立组件,直接用自己的块,不要加父块前缀。