Vue组件data为什么是函数,面试的时候被问到了,感觉解释的不太清楚,借博客整理一下
什么是Vue组件
这里先借用官方的解释:
组件是可复用的 Vue 实例,且带有一个名字:在这个例子中是 <button-counter>
,如下:
1
2
3
4
5
6
7
8
|
Vue.component('button-counter', {
data: function () {
return {
count: 0
}
},
template: '<button v-on:click="count++">You clicked me {{ count }} times.</button>'
})
|
data为啥么是函数不是对象
官方已经解释了,一个vue组件就是一个vue实例。
在JS当中实例是通过构造函数来创建的,每个构造函数可以new
出很多个实例,那么每个实例都会继承原型上的方法或属性。
vue的data数据其实是vue组件原型上的属性,数据存在于内存当中
vue组件为了保证每个实例上的data数据的独立性,规定了必须使用函数,而不是对象。
因为使用对象的话,每个实例(组件)上使用的data数据是相互影响的,这当然就不是我们想要的了。对象是对于内存地址的引用,直接定义个对象的话组件之间都会使用这个对象,这样会造成组件之间数据相互影响。
不使用函数和使用函数示例
不使用函数
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
|
// 创建一个简单的构建函数
var MyComponent = function() {
}
// 原型链对象上设置data数据,为里为Object
MyComponent.prototype.data = {
name: 'abc',
age: 20,
}
// 创建两个实例:小明,小红
var xiaoming = new MyComponent()
var xiaohong = new MyComponent()
// 默认状态下小明和小红的年龄一样
console.log(xiaoming.data.age === xiaohong.data.age) // true
// 改变一下小明的年龄
xiaoming.data.age = 30;
// 打印下小红的年龄,发现因为改变了小明的年龄,结果造成小红的年龄也变了
console.log(xiaoming.data.age)// 30
console.log(xiaohong.data.age) // 30
|
这是因为小红和小明的data
都引用的是同一个内存地址
使用函数
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
|
// 创建一个简单的构建函数
var MyComponent = function() {
// ... code here
this.data = this.data();
}
// 原型链对象上设置data数据,为里为Object
MyComponent.prototype.data = function(){
return {
name: 'abc',
age: 20,
}
};
// 创建两个实例:小明,小红
var xiaoming = new MyComponent()
var xiaohong = new MyComponent()
// 默认状态下小明和小红的年龄一样
console.log(xiaoming.data.age === xiaohong.data.age) // true
// 改变一下小明的年龄
xiaoming.data.age = 30;
// 打印下小红的年龄,发现因为必变了小明的年龄,结果造成小红的年龄也变了
console.log(xiaoming.data.age)//30
console.log(xiaohong.data.age) // 20
|
使用函数后,使用的是data()函数,data()函数中的this指向的是当前实例本身
总结
当一个组件被定义, data 必须声明为返回一个初始数据对象的函数,因为组件可能被用来创建多个实例。如果 data 仍然是一个纯粹的对象,则所有的实例将共享引用同一个数据对象!通过提供 data 函数,每次创建一个新实例后,我们能够调用 data 函数,从而返回初始数据的一个全新副本数据对象。