专栏首页小码农学习笔记Vue 面试官问:模板编译原理
原创

Vue 面试官问:模板编译原理

模板编译

前置知识点:with 语法

首先复习一个 JS 的冷门知识点:with 语法。

常规作用域查找变量方式:

const obj = {a: 100, b: 200}

console.log(obj.a)
console.log(obj.b)
console.log(obj.c) // undefined

使用 with 后,能改变 {} 内自由变量的查找方式:将 {} 内自由变量当作 obj 的属性来查找:

with(obj) {
  console.log(obj.a)
  console.log(obj.b)
  console.log(obj.c) // 会报错
}

在平时开发中,一般慎用 with 语法,这是因为它打破了作用域规则,使代码易读性变差了。但这里把它作为前置知识点是因为模板编译中用到了。

Vue 模板被编译成什么

  • Vue 的模板不是 html,因为它有指令、插值、JS 表达式,能实现判断、循环;
  • html 是标签语言,只有 JS 才能实现判断、循环。

因此,模板一定是转换为某种 JS 代码,即编译模板。

Vue 模板编译过程

  • 模板编译为 render 函数,执行 render 函数返回 vnode;
  • 基于 vnode 再执行 patch 和 diff;
  • 使用 Webpack 时,vue-loader 会在开发环境下编译模板(目前业内主流);否则会在浏览器运行时中编译(单独在页面中引入 vue.js 使用)。

用代码来解释编译过程:

// Step1: 一个 template,使用了插值语法
const template = `<p>{{message}}</p>`

// Step2: 上述 template 被编译后,得到 JS 代码如下
// with 语法,后面的自由变量的查找都会变成 this 的查找
// this 指向 vm 实例: vm = new vue({...})
with(this){return createElement('p',[createTextVNode(toString(message))])}

// Step3: 执行上述函数后,返回 vnode
// 类似 snabbdom 的 h 函数: h('p', {}, [...]) => vnode

// Step4: 渲染和更新

vue 组件中使用 render 代替 template

通过 template 来定义 Vue 组件:

Vue.component('heading', {
  template: `<h3><a name="headerId" href="#headerId">this is a tag</a></h3>`
})

通过 render 属性来定义 Vue 组件,需要定义一个函数,参数为 createElement

createElement 类似于前面介绍的编译后的函数体,它的第一个参数是标签,第二个参数是属性(可不写),第三个参数是子元素。

Vue.component('heading', {
  render: function(createElement) {
    return createElement(
      'h' + this.level,
      [
        createElement('a', {
          attrs: {
            name: 'headerId',
            href: '#' + 'headerId'
          }
        }, 'this is a tag')
      ]
    )
  }
})

在有些复杂情况中,不能用 template,可以考虑用 render


文章持续更新,本文 GitHub 前端修炼小册 已经收录,欢迎 Star。如对文章内容有不同见解,欢迎留言交流。

原创声明,本文系作者授权云+社区发表,未经许可,不得转载。

如有侵权,请联系 yunjia_community@tencent.com 删除。

我来说两句

0 条评论
登录 后参与评论

相关文章

  • Vue中模板编译原理?

    如何将template转换成render函数(这里要注意的是我们在开发时尽量不要使用template,因为将template转化成render方法需要在运行时进...

    美食江湖
  • Vue中的模板编译原理

    1.将模板解析为AST(抽象语法树)—— 解析器。 2.遍历AST标记静态节点 —— 优化器。 3.使用AST生成渲染函数 —— 代码生成器)。

    刘亦枫
  • Vue 面试官问:前端路由原理

    H5 history 模式需要 server 端配合,可参考后端配置例子。无论访问哪个路由,都返回 index.html 页面,再由前端通过 history.p...

    文渊同学
  • Vue2.0模板编译原理

    写过 Vue 的同学肯定体验过, .vue 这种单文件组件有多么方便。但是我们也知道,Vue 底层是通过虚拟 DOM 来进行渲染的,那么 .vue 文件的模板到...

    若川
  • Vue3 模板编译原理

    其中 compiler-core 模块是 Vue 编译的核心模块,并且是平台无关的。而剩下的三个都是在 compiler-core 的基础上针对不同的平台作了适...

    谭光志
  • 深入理解 Vue 模板渲染:Vue 模板反编译

    熟悉 vue 的同学应该都知道,vue 单文件模板中一般含有三个部分,template,script,style。

    WecTeam
  • 找准切入点,调试看源码,事半功倍

    说到看源码,很多人都有个误区,觉得看源码必须要到 github 上把完整的代码 clone 下来,认为只有把完整的代码下载下来,才能开始愉快的学习。

    若川
  • 【前端面考面试官系列】入门Vue全家桶

    达达回答:Vue的安装可以从两个方面进行安装,第一种是CDN引入,第二种是NPM安装。

    达达前端
  • 太原面经分享:如何在vue面试环节,展示你晋级阿里P6+的技术功底?

    一年一度紧张刺激的高考开始了,与此同时,我也没闲着,奔走在各大公司的前端面试环节,不断积累着经验,一路升级打怪。

    闰土大叔
  • Vue.js——60分钟browserify项目模板快速入门

    在之前的一系列vue.js文章,我们都是用传统模式引用vue.js以及其他的js文件的,这在开发时会产生一些问题。

    Vincent-yuan
  • 如何在Vue面试环节,证明自己值月薪15K?

    回想一下,自己平时面试的坐姿,你在面试官眼里,大概是什么形象,可能是工程师,也可能是键盘侠,或者找麻烦的。

    闰土大叔
  • 面试官:Vue3有了解过吗?能说说跟Vue2的区别吗?

    「Vue 新版本的理念成型于 2018 年末,当时 Vue 2 的代码库已经有两岁半了。比起通用软件的生命周期来这好像也没那么久,但在这段时期,前端世界已经今昔...

    @超人
  • 手写Vue-router核心原理,再也不怕面试官问我Vue-router原理

    在 Web 前端单页应用 SPA(Single Page Application)中,路由描述的是 URL 与 UI 之间的映射关系,这种映射是单向的,即 UR...

    秋风的笔记
  • Kbone原理解析 & 小程序技术选型

    首先我们来看下普通Web端框架,以Vue框架为例,一份Vue模板对应一个组件,在代码构建阶段编译成调用Dom接口的JS函数,执行此JS函数就会创建出组件对应的D...

    binnie
  • 14 上线后不想让人看到源码怎么做?

    在安装了Vue Devtools之后,在chrome浏览器开发模式下,打开vue面板,选择组件,然后就可以直接查看和修改data数据:

    程序员LIYI
  • vue组件对象字面量传值的注意啦!

    前面汇总过 「vue组件引用传值的最佳实践」,对于 vue2 版本存在一个严重的性能问题,需要格外注意:对象字面量的传递

    奋飛
  • vue组件对象字面量传值的注意啦!

    前面汇总过 「vue组件引用传值的最佳实践」,对于 vue2 版本存在一个严重的性能问题,需要格外注意:对象字面量的传递

    奋飛
  • Vue.js入门手册整理

    webpack简介,webpack是一个前端资源加载/打包工具,将各种js/css/html代码最后打包编译到一起。vuejs已经集成

    SmileNicky
  • Kbone原理解析与小程序技术选型

    https://developers.weixin.qq.com/community/develop/article/doc/0006a6326b8d38e56...

    zz_jesse

扫码关注云+社区

领取腾讯云代金券