为什么 data 必须为函数
前言
Vue.js 是前端热门的UI框架。目前国内的前端团队一般都是 Vue.js、React 二选一。
理解 Vue.js 的技术细节,既有助于日常工作开发,也是一个很好的敲门砖。
背景
我在社区里搜索过 Vue.js 相关的文章,发现不少高赞的文章都是水文,或者是年久失修的老文。
如果读者不明所以,直接照本宣科,面试的结果必然是凉凉。因此,我还是建议读者们自行阅读源码,或者看一些源码解析的文章(这里我推荐一下黄老师的源码解析),不会一知半解,被水文坑害。本文也是笔者自己的 Vue.js 相关的底层原理的认知总结,如有纰漏,或者错误,烦请指正。
常见问题
Vue.js 里 data 为什么必须是函数?
因为最近几年微信小程序也挺火,因此这个问题可以联想到 微信小程序的 data 怎么是对象而不是函数呢?
vue 的官方也有提到,在同时渲染多个相同组件时,为了避免组件之间的数据互相影响,因此需要使用函数返回的对象来隔离。
其实,从上面官网的解释很容易理解。对象是引用类型,被多个组件使用,必然会互相影响。所以不要被官网初始化 Vue 实例的例子误导:
var app = new Vue({
el: '#app',
data: {
message: 'Hello Vue!'
}
})
因为这个 Vue 实例是唯一的,所以不存在互相影响的问题。
所以可以得出结论1:data 使用函数是避免多个组件实例之间互相影响
使用组件有两种方式:
- 全局注册;使用
Vue.component()
- 局部注册;在组件对象里使用
components
属性
下面以局部注册举例。
渲染页面时,Vue.js 会解析 HTML
的tag,如果此时发现不是原生 tag,就会从 components
属性里获取对应的组件声明,如果找到,则使用 createComponent
函数创建组件,将组件声明通过 Vue.extend
(源码位置:src/core/global-api/extend.js
)来初始化构造函数 Ctor
,这个 Ctor
将会被复用。
由此可见,我们的组件声明并不是直接用来当构造函数的,而是构造函数的入参。因此使用 data 函数可以避免数据的混淆,也避免了 Vue.js 需要对 data 进行深复制的繁琐操作,提升了执行速度。