写文章不容易,点个赞呗兄弟
专注 Vue 源码分享,文章分为白话版和 源码版,白话版助于理解工作原理,源码版助于了解内部详情,让我们一起学习吧
研究基于 Vue版本 【2.5.17】
如果你觉得排版难看,请点击 下面链接 或者 拉到 下面关注公众号也可以吧
【Vue原理】Compile - 源码版 之 optimize 标记静态节点
compile 三大步骤,parse 我们已经讲完了
现在到了第二步了,optimize这一步的内容好像不太多,但是非常重要,于是是一个更新性能优化, 非常重要
先来看看 optimize 在什么位置,就在 parse 处理完之后,generate 之前
var ast = parse(template.trim(), options);
if (options.optimize !== false) {
optimize(ast, options);
}
var code = generate(ast, options);
上面这段代码在函数 baseCompile 中,如果想了解的,看这里 Compile - 从新建实例到 compile结束的主要流程
而 optimize 的作用是什么呢?
Vue官方注释
优化器的目标
遍历生成的模板AST树,检测纯静态的子树,即永远不需要更改的DOM。
一旦我们检测到这些子树,我们可以:
1、把它们变成常数,这样我们就不需要了在每次重新渲染时为它们创建新的节点
2、在修补过程中完全跳过它们。
那是怎么做的呢?
给静态ast节点设置属性 static,当节点时静态是
el.static = true
下面就来看下源码
function optimize(root, options) {
if (!root) return
// first pass: mark all non-static nodes.
markStatic$1(root);
// second pass: mark static roots.
markStaticRoots(root);
}
里面主要调用了两个函数,这两个函数会分别分析
但是在此之前,我们先来看一个函数,这个函数就是 判断静态节点的 主力函数
直接传入 ast 节点,各种组合判断,然后给 ast 节点添加上 static 属性
function isStatic(node) {
// 文字表达式
if (node.type === 2) return false
// 纯文本
if (node.type === 3) return true
return (
// 设置了 v-pre 指令,表示不用解析
node.pre ||
(
!node.hasBindings && // 没有动态绑定
! node.if && !node.for && // 不存在v-if ,v-for 指令
! ['slot&