前端进阶之旅前端进阶之旅
基础篇
进阶篇
高频篇
精选篇
手写篇
面经篇
AI 篇
原理篇
每日一题
小程序题库
知识卡片
  • 场景篇按分类整理的大前端场景考点
  • 历年面经按年份追踪真实考点
  • 算法题库NEW在线编码即时判题
  • 专项自测100 题快速查漏
  • 前端基础
    • HTTP从报文一路讲到 HTTPS
    • 浏览器渲染、事件循环、进程
    • 计算机基础Linux、网络、操作系统
  • 进阶专项
    • 设计模式23 种模式怎么用
    • 前端系统进阶学习大型项目工程化
    • 前端综合文章长期沉淀的实践文
  • 工程与工具
    • Node学习指南从环境搭建到服务端
    • NPM工作流script、依赖与发布
    • Docker容器化部署上手
    • Canvas图形与动画实战
  • 路线与导图
    • 思维导图知识点全景图
    • 学习路线按图索骥不跑偏
  • 动态
    • 公众号动态公众号历史文章
    • 博客动态站长的技术博客
    • 开发者导航常用工具与文档站
  • AI 助手随时提问,即时解析
  • AI 模拟面试模拟真实面试 + 报告
  • AI 知识地图串起全站知识点
  • AI 定制路线按你的简历现排
AI 热点
旧版
基础篇
进阶篇
高频篇
精选篇
手写篇
面经篇
AI 篇
原理篇
每日一题
小程序题库
知识卡片
  • 场景篇按分类整理的大前端场景考点
  • 历年面经按年份追踪真实考点
  • 算法题库NEW在线编码即时判题
  • 专项自测100 题快速查漏
  • 前端基础
    • HTTP从报文一路讲到 HTTPS
    • 浏览器渲染、事件循环、进程
    • 计算机基础Linux、网络、操作系统
  • 进阶专项
    • 设计模式23 种模式怎么用
    • 前端系统进阶学习大型项目工程化
    • 前端综合文章长期沉淀的实践文
  • 工程与工具
    • Node学习指南从环境搭建到服务端
    • NPM工作流script、依赖与发布
    • Docker容器化部署上手
    • Canvas图形与动画实战
  • 路线与导图
    • 思维导图知识点全景图
    • 学习路线按图索骥不跑偏
  • 动态
    • 公众号动态公众号历史文章
    • 博客动态站长的技术博客
    • 开发者导航常用工具与文档站
  • AI 助手随时提问,即时解析
  • AI 模拟面试模拟真实面试 + 报告
  • AI 知识地图串起全站知识点
  • AI 定制路线按你的简历现排
AI 热点
旧版
首页程序员面试题库父子外边距塌陷 防止 margin collapse
CSS盒模型与排版

给子元素加 margin-top,为什么整个父元素一起掉下来了?

父元素上边没有 padding、border 隔开时,第一个子元素的 margin-top 会和父元素的 margin-top 合并成一个,显示在父元素外面,看起来就是父元素被拉了下来。给父元素加 padding-top、border-top,或者让它建立 BFC(最干净的是 display: flow-root),就能把两个外边距隔开。

前端进阶之旅 · 一题精讲更新于 2026.09.29
CSS#盒模型与排版
先看核心答案读代码示例
理解线索

父子外边距合并的三个关键

  1. 相邻条件父元素的上边框和第一个子元素的上外边距之间没有 padding、border、行内内容隔开
  2. 合并取值两个正值取大的,一正一负相加,两个负值取绝对值大的
  3. BFC父元素建立新的块级格式化上下文后,子元素的外边距被关在里面,不再和父元素合并

底部同样会合并:父元素高度是 auto 时,最后一个子元素的 margin-bottom 也会跑到父元素外面,把下面的兄弟元素推远。

核心回答

先记住这个答案

在普通文档流里,如果父元素的顶部没有 padding、border,也不是 BFC,那它的 margin-top 和第一个子元素的 margin-top 就是相邻的,会合并成一个外边距,取两者中较大的值。这个合并后的外边距显示在父元素的外面,于是看起来是子元素的外边距把父元素整体往下推,父元素的背景顶部和子元素贴在一起。解决办法是在两个外边距之间放点东西隔开,或者让父元素建立 BFC,推荐 display: flow-root。

  • 父子上外边距可能合并
  • 合并后取两者较大值,并显示在父元素外面
  • 首选修法是父元素 display: flow-root
  • flex 和 grid 容器里子项的外边距不会和容器合并

复现一下:子元素的外边距跑到了外面

一个有背景色的卡片,里面第一个元素是标题,给标题加 margin-top 想让它离卡片顶部远一点。

标题的外边距把卡片推了下去HTML
<style>
  .card { background: #eef; }
  .card h2 { margin-top: 24px; }
</style>

<div class="card">
  <h2>标题</h2>
  <p>正文</p>
</div>
<!-- 预期:卡片顶部和标题之间有 24px 的浅蓝色 -->
<!-- 实际:标题紧贴卡片顶部,24px 空白出现在卡片上方 -->

.card 顶部没有 padding 和 border,自己的 margin-top 是 0,和 h2 的 24px 合并后是 24px。这个合并后的外边距属于整个组合,渲染在 .card 外面,所以空白在卡片背景上方,而不是卡片里面。 h2 本身就有浏览器默认的上外边距,所以哪怕不写这行 CSS,没清过默认样式的项目也会遇到卡片顶部莫名多出一截空白。

合并的条件和取值

外边距合并只发生在普通流里的块级盒子之间,而且两个外边距之间必须是「挨着」的。父子之间,下面任何一样东西都能把它们隔开:父元素的 padding-top、border-top、父元素里排在子元素前面的文字或行内元素、清除浮动产生的间隙。

合并后到底是多少
两个都是正数时取较大的,24px 和 10px 合并是 24px,不是 34px。一正一负时相加,24px 和 -10px 合并是 14px。两个都是负数时取绝对值大的那个。这套规则对兄弟元素之间的合并也一样。 父元素是 BFC(块级格式化上下文,一个独立的布局区域,里面的外边距不会和外面的合并)时,也不会合并。能让父元素变成 BFC 的有 display: flow-root、overflow 取 hidden 或 auto、浮动、绝对定位、display: inline-block 等。

几种修法和各自的代价

修法都不难,区别在于有没有副作用。

按推荐程度排
第一选择是父元素加 display: flow-root。它唯一的作用就是建立 BFC,没有别的副作用,专门为这类场景设计。 第二是给父元素加 padding-top,把原来写在子元素上的间距挪到父元素上。卡片这类组件本来就该用内边距控制内容和边缘的距离,这个改法语义上最合理。 第三是 border-top: 1px solid transparent,能用,但多出 1px 高度,属于绕路。 overflow: hidden 也能修,但它会裁掉阴影、下拉菜单这类溢出的内容,还会让父元素成为滚动容器,影响里面的 position: sticky。以前常用它,现在有 flow-root 就没必要了。 另外,把父元素改成 flex 或 grid 容器,子项的外边距不会和容器合并。很多组件本来就是 flex 布局,所以会觉得「这个问题怎么消失了」。
回答前,多想一步

容易答错的地方

以为合并后是两个外边距相加
正数之间取最大值,不是求和。父元素 margin-top: 10px、子元素 margin-top: 24px,最终父元素上方只有 24px。
以为 overflow: clip 也能修
overflow: clip 只裁剪,不让元素成为滚动容器,也不建立 BFC,外边距照样合并。能修的是 hidden、auto、scroll。
以为只有顶部会合并
底部同样会合并。父元素高度是 auto、底部没有 padding 和 border 时,最后一个子元素的 margin-bottom 会跑到父元素下面。表现是父元素的背景没包住那段空白,下一个兄弟元素被推远。
试着用自己的话回答

面试官还会怎么问?

水平方向的外边距会合并吗?

不会。外边距合并只发生在块方向,也就是横排文字下的上下方向。左右外边距永远是相加的。

空元素自己的上下外边距会合并吗?

会。一个没有内容、没有高度、没有 padding 和 border 的空块元素,它的 margin-top 和 margin-bottom 会合并成一个,并且还可能继续和相邻元素的外边距合并。列表里偶尔出现一个空的 <p>,就会造成这种意料之外的间距。

实际项目里怎么避免反复踩这个坑?

组件内部统一用 padding 控制内容和边框的距离,子元素之间的间距用 flex 或 grid 的 gap,只在一个方向上给外边距。这样父子之间根本没有两个外边距相遇的机会。

从一道题,走向一组知识

把知识连起来

盒模型与排版

position: relative 配 z-index: auto,会创建层叠上下文吗?

元素位置不对先查外边距,元素被遮住再查层叠。那一题讲 position: relative 配 z-index: auto 为什么不创建层叠上下文。

盒模型与排版

相对定位的元素设置了 top、left,旁边的元素会跟着动吗?

两题都在讲「看到的位置」和「文档流里占的位置」不一致,那一题是 position: relative 偏移不影响其他元素。

参考资料

  • CSS:盒模型与排版参考资料

示例用于理解所注明的运行环境与边界;延伸学习可结合原文中的更多案例。

本题目录
  1. 先记住这个答案
  2. 复现一下:子元素的外边距跑到了外面
  3. 合并的条件和取值
  4. 几种修法和各自的代价
  5. 容易答错的地方
  6. 面试官还会怎么问
  7. 把知识连起来
读懂,再试着讲出来

先看核心答案,再读代码。最后展开追问,检查自己有没有遗漏边界。

试着回答追问
浏览全部面试题理解原理,也关注真实的使用场景。回到顶部 ↑