跳转到内容

卓望

刀刀

8/4/2025

0 字

0 分钟

一面

Q:说一下事件循环。

我的回答

js 是单线程语言,会先执行同步任务,执行完毕后去看异步任务队列,有没有需要执行的任务,有的话依次执行。底层逻辑是写死了一个for循环,不断去查看这个队列,这个就是事件循环。

Q:说一下浏览器渲染原理

推荐阅读:浏览器渲染原理

Q:光栅化是在哪个进程处理的?

我的回答

渲染吧?

Q:渲染主线程?那最后画的阶段是在哪个主线程执行?

我的回答

应该是画才是在渲染主线程执行,光栅化我有点忘了。

Deepseek 回答

在浏览器中(如WebGL/Canvas),渲染进程(Renderer Process),光栅化通常在浏览器的渲染进程中处理:

  • 当页面使用 Canvas 2D、WebGL 或 CSS 3D 变换时,渲染进程的合成线程(Compositor Thread) 负责光栅化(将矢量图形/3D图元转换为像素)。

  • 若启用GPU加速,光栅化会通过 GPU 进程(GPU Process)提交给显卡硬件执行。

Q:那重排是发生在哪个阶段?

我的回答

重排发生在 layout 布局树那块。

Q:具体发生了什么?发生了什么导致它重排?

我的回答

修改了 DOM 树,例如宽高、left、right等布局,都导致重新计算布局。因此最好使用 transform 代替,性能会更好

Q:你说 transform,transform 是哪个阶段?

我的回答

最后画,也就是重绘的阶段

我的回答

script 会堵塞,所以最好不要把 script 写在 HTML 前面,或者添加属性符 defer 或 async。第二问我的理解是 script 标签是脚本,需要获取真实 DOM,因此需要用单线程处理,例如不能同时执行两个脚本。

Deepseek 回答

阻塞解析的核心原因

  1. DOM 修改风险

    JavaScript 可以通过 document.write()、innerHTML 或 DOM API 直接修改文档结构。如果浏览器边解析边执行 JS,可能造成:

    • 已解析的 DOM 被破坏

    • 资源加载顺序混乱

    • 渲染树构建错误

  2. CSSOM 依赖

    若 JavaScript 尝试访问 CSS 样式(如 element.style 或 CSSOM API),浏览器需确保所有前置 CSS 已加载和解析(CSSOM 构建完成)。这要求:

    • 暂停 JS 执行直到 CSS 解析完成

    • 连带阻塞 HTML 解析

而 link 不会阻塞,是因为:

  1. CSS 不改变 DOM 结构

    • CSS 只影响元素样式,无法修改 DOM 树结构(不能增删节点)

    • 浏览器可以安全地并行解析 HTML 和下载/解析 CSS:

  2. 渲染分离原则

    • 浏览器采用 "解析-渲染分离"架构:

      • 解析线程:持续解析 HTML 构建 DOM

      • 渲染线程:等待 CSSOM 构建完成后才绘制页面

    • 即使 CSS 未加载完,DOM 树仍可继续构建(只是不显示)

  3. 预加载扫描器(Preloader)优化

    现代浏览器会启动 后台预扫描线程:

    • 发现 <link> 标签后立即异步下载 CSS

    • 不阻塞主解析线程

Q:说一下选择器的优先级

我的回答

  1. !important
  2. 内联样式
  3. id选择器
  4. 类选择器、伪类选择器、属性选择器
  5. 元素选择器、伪元素选择器
  6. 继承

Q:CSS属性值的计算过程有了解过么?

我的回答

不清楚

Deepseek 回答

主要流程 主要流程

阶段 1:指定值 (Specified Value):浏览器确定应该应用哪个值(不考虑是否有效或可继承)

确定来源优先级(从高到低):

  1. !important 声明
  2. 作者样式表(开发者写的 CSS)
  3. 行内样式 > ID 选择器 > 类/属性选择器 > 标签选择器 > 通配符
  4. 用户样式表(浏览器扩展/用户自定义)
  5. 用户代理样式表(浏览器默认样式)
  6. 继承值(从父元素继承)

阶段 2:计算值 (Computed Value):将相对单位/关键字转换为绝对单位(但尚未布局)

转换规则:

相对单位/关键字转换结果
em, rempx(基于字体大小)
%→ 保留(需布局计算)
inherit→ 父元素的计算值
initial→ 属性默认值
currentColor→ 当前 color 的计算值
var(--custom)→ 自定义属性解析后的值
示例代码:
css
.box {
  font-size: 16px;
  padding: 2em;     /* 计算值 → 32px */
  width: 80%;       /* 保留 % (需布局) */
  color: inherit;   /* 继承父元素颜色 */
}

阶段 3:使用值 (Used Value):完成布局计算后的实际值(所有相对单位绝对化)

关键转换:

属性类型转换逻辑
百分比宽度/高度→ 根据包含块尺寸计算为 px
auto 值→ 根据布局算法计算实际值
vh/vw/vmin→ 转换为视口比例的 px

示例代码:

html
<div class="parent" style="width: 200px">
  <!-- 最终计算width宽度为100px -->
  <div class="child" style="width: 50%"></div>
</div>

阶段 4:实际值 (Actual Value):浏览器根据设备限制进行的最终适配(不改变使用值含义)

常见调整:

  1. 子像素渲染:width: 100.5px → 实际渲染为亚像素
  2. 颜色舍入:#88aaff → 转换为设备支持的色域
  3. 字体回退:指定字体缺失时使用备用字体
  4. 整数舍入:z-index: 2.3 → 实际值 2

示例代码:

css
.element {
  width: 33.333%;  /* 使用值可能是 100.666px(根据抗锯齿策略) */
}

Q:说一下 Vue 2 和 3 响应式原理的区别?

Q:有没有了解过工程化?

我的回答

比如 vite 项目有设置过 vite.config.js,重写了打包命名规则,过滤掉 _ 等特殊符号

Q:项目中有没有遇到过什么难题?