探讨:JavaScript ECAMScript5 新特性之get/set访问器(2)

var object={ _name:"Daisy", get name(){//这里的方法名name ,就表示定义了一个name属性(因此才能通过object.name访问),只定义了getter访问器,没有定义[[value]]值 return this._name; }//get,set方法只是属性的特性 ,不是对象方法,决定属性能否、怎么读写 }; alert(object.name);// Daisy这里去掉下划线 方法就是Daisy ;加上就是undefined object.name="jack";//只定义了getter访问器,因此只能读不能写 alert(object.name);//Daisy

以上两种方法等效。注意的是以上两种方法object对象当中都将有有两个属性:_name(有初始值) name(无初始值),通过浏览器控制台可以看到

探讨:JavaScript ECAMScript5 新特性之get/set访问器

那么这个name属性实在什么时候定义的呢?我们知道Object.defineProperty(object,pro,{})可以给对象定义一个新属性pro,既然get pro(){}/set pro(){}和Object.defineProperty(object,pro,{})等效,则也会定义一个新属性pro .这就是为什么object里面有两个属性的原因。

(3)在此篇文章中网络之美 JavaScript中Get和Set访问器的实现代码关于标准标准的Get和Set访问器的实现:引发的思考

我自己也写了一个一样的例子

function Foo(val){ this.value=val;//定义了value属性 并没有定义_value } Foo.prototype={ set value(val){//注意方法名和属性名相同,在prototype里定义了value属性 this._value=val; }, get value(){//方法名和属性名相同,在prototype里面定义了value属性和它的get 特性 return this._value; } }; //访问器返回和设置的都是_name,这里并没有定义_name属性为什么也可以读可以写????      var obj=new Foo("hello");      alert(obj.value);//"hello"      obj.value="yehoo";      alert(obj.value);//"yehoo"

为了解决以上这个疑问,做了很多测试,我们一一来看:

先看这个例子,在prototype里面只定义get 特性,在obj.value读value属性时,在实例里面寻找没有,然后在原型里面找到,调用的是原型的get方法,只能读不能写

function Foo(val){ this._value=val;//这里 的属性是带下划线的,初始化实例对象的_value属性,_value属性可读可写 } Foo.prototype={ // set value(val){//注意方法名和属性名相同,在prototype里定义了value属性 // this._value=val; // }, get value(){//方法名和属性名相同,在prototype里面定义了value属性和它的get 特性 return this._value; } }; var obj=new Foo("hello"); alert(obj.value);//hello 访问的是prototype里面的value 属性 obj.value="yehoo";//只定义了name 属性的get 特性,因此只能读不能写,写入失效 alert(obj.value);//hello

如果构造函数里面this._value 去掉下划线,在prototype里面定义的value属性,定义了get 特性。依然可以控制value属性的读写 。也就是说obj.value访问属性时,会调用get方法,先在对象本身寻找,如果没有,再到prototype寻找,如果都没有才算没有定义,默认的既可读又可写

function Foo(val){ this.value=val;//在原型里面只定义了value的get特性,因此这里写入失效 } Foo.prototype={ // set value(val){//注意方法名和属性名相同,在prototype里定义了value属性的set特性 // this._value=val; //}, //value:"hah",//即使手动写入value值,由于get方法返回的是this._value,因此也不能正确读取value:"hah" //只要声明了get pro (){}和set pro (){}属性就都能读能写,但是如果函数定义错误,依然不能按要求访问到正确的属性值 get value(){//方法名和属性名相同,在prototype里面定义了value属性和它的get 特性 return this._value; } }; var obj=new Foo("hello");//"hello"没有写入成功 alert(obj.value);//undefined obj.value="yehoo";//只定义了get 特性,因此只能读不能写,写入失效 alert(obj.value);//undefined

为了证明上面例子是可读不可写的:手动写入_value:"hah",就可以读取value 但不能写入。

function Foo(val){ this.value=val;//在原型里面只定义了value的get特性,因此这里写入失效 } Foo.prototype={ // set value(val){//注意方法名和属性名相同,在prototype里定义了value属性的set特性 // this._value=val; //}, _value:"hah",//即使手动写入value值,由于get方法返回的是this._value,因此也不能正确读取value:"hah" //只要声明了get pro (){}和set pro (){}属性就都能读能写,但是如果函数定义错误,依然不能按要求访问到正确的属性值 get value(){//方法名和属性名相同,在prototype里面定义了value属性和它的get 特性 return this._value; } }; var obj=new Foo("hello");//"hello"没有写入成功 alert(obj.value);//"hah" obj.value="yehoo";//只定义了get 特性,因此只能读不能写,写入失效 alert(obj.value);//"hah"

内容版权声明:除非注明,否则皆为本站原创文章。

转载注明出处:https://www.heiqu.com/wzpssd.html