ES5中的双向绑定
ES5中的对象属性类型有两种:分别是数据属性和访问器属性
一,数据属性
数据属性包含一个数据值的位置。在这个位置可以读取和写入值。数据属性有4个描述其行为的特性
1,configurable:表示能否通过delete删除属性而重新定义属性,能否修改属性的特性,或者能否把属性修改为访问器属性;如果设置为true表示可以删除,如果是false不能被删除,默认为false
//为false的情况下无法删除const obj={name:"张三"}Object.defineProperty(obj,'name',{configurable:false})delete obj.nameconsole.log(obj.name)//张三//为true的情况下可以删除const obj={name:"张三"}Object.defineProperty(obj,'name',{configurable:true})delete obj.nameconsole.log(obj.name)//undefined
2,Enumerable:表示能否通过for-in循环返回属性;设置为true可以被枚举,设置为false,不能被枚举,默认为false
//为false无法被枚举const obj={name:"张三",}Object.defineProperty(obj,'name',{enumerable:false})for(let key in obj){console.log(obj[key]) //无任何输出}//为true可以被枚举const obj={name:"张三",}Object.defineProperty(obj,'name',{enumerable:false})for(let key in obj){console.log(obj[key])//张三}
3,Writable:表示能否修改这个属性的值;设置为true可以被重写,设置为false,不能被重写,默认为false
//默认不能重写const obj={}Object.defineProperty(obj,'name',{value:'张三'})console.log(obj.name)//张三obj.name='李四'console.log(obj.name)//张三//设置为true可以重写const obj={}Object.defineProperty(obj,'name',{value:'张三',writable:true})console.log(obj.name)//张三obj.name='李四'console.log(obj.name)//李四
4,value:包含这个属性的值;
const obj={name:'张三'}Object.defineProperty(obj,'name',{value:'李四'})//改变obj.name的值为李四,输出来李四console.log(obj.name)//李四//如果没有设置值,还是返回原来的值const obj={name:'张三'}Object.defineProperty(obj,'name',{})console.log(obj.name)//张三
要修改属性的默认特性,必须使用ES5中的Object.defineProperty()方法,这个方法接收三个参数,属性所在的对象,属性的名字和一个描述符对象,描述符对象的属性就是上面的4个
二,访问器属性
访问器属性不包含数据值,它们是一对getter和setter函数,在读取访问器属性时,会调用getter函数,这个函数负责返回有效的值;在写入访问器属性时,会调用setter函数并传入新值。这个函数负责如何处理数据。访问器属性有4个特性 configurable和Enumerable(这两个属性和上面的用法相同)
1,Get:在读取属性时调用函数:默认为undefined
2,Set:在写入属性时调用函数:默认为undefined
注意:使用访问器属性中 getter或 setter方法,不能使用 writable 和 value 这两个配置项
const obj={}let age=20Object.defineProperty(obj,'age',{get:function () {console.log("读取属性值的时候调用")return age},set:function (newValue) {console.log("写入属性值的时候调用")age=newValue}})console.log(obj.age)//20//设置了属性值会调用set方法obj.age=30console.log(obj.age)//30
实现一个小案例
<!DOCTYPE html>
<html lang="en">
<head><meta charset="UTF-8"><title>Title</title>
</head>
<body>
<input type="text" id="demo">
<div id="test">test</div>
</body>
<script>const obj={}//用于设置obj的属性值为nameObject.defineProperty(obj,'name',{//获取到设置set的值//读取到obj.name属性值的更改set:function(value){document.getElementById('test').innerHTML=value}})console.log(obj.name)//获取到文本框中的值并赋给obj.namedocument.getElementById('demo').oninput=function (e) {obj.name=e.target.value}
</script>
</html>
三,定义多个属性
Object.defineProperties()方法一次设置或修改多个属性。这个方法接受两个对象参数:第一个对象是要添加和修改其属性的对象,第二个对象的属性与第一个对象中要添加或修改的属性一一对应。
const obj4={_name:"王五",_age:33}Object.defineProperties(obj4,{age:{get(){console.log("监听到读取age属性")return this._age},set(value){console.log("监听到设置age属性")this._age=valuereturn this._age}},name:{get(){console.log("读取到name属性")return this._name},set(value){console.log("监听到正在设置name属性")this._name=valuereturn this._name}}})console.log(obj4.age,obj4.name)//33 王五obj4.age=34obj4.name="哈哈"console.log(obj4.age,obj4.name)//34 '哈哈'
四,读取属性的特性
es5中Object.getOwnPropertyDescriptor()方法,可以取得给定属性的描述符,这个方法接受两个参数;属性所在的对象和要读取其描述符的属性名称。返回值是一个对象,如果是访问器属性,这个对象的属性性有configurable,enumerable,get,set;如果是数据属性,这个对象的属性有configurable,enumerable,writable,value
const obj2={name:30}const descriptor=Object.getOwnPropertyDescriptor(obj2,'name')console.log(descriptor)//是一个对象,包含如下特性
ES6中的双向绑定
未完待续...