欢迎您访问程序员文章站本站旨在为大家提供分享程序员计算机编程知识!
您现在的位置是: 首页  >  IT编程

前端开发JS——对象与原型

程序员文章站 2022-03-26 13:24:35
27、创建对象 ①工厂模式批量创建对象 缺点:无法对象识别,即所有对象都是Object类型;方法内存空间浪费/封装不太完善 function sayName(){ //可以有效节省内存空间 console.log(this.name); } function createObject(name, a ......
27、创建对象
①工厂模式批量创建对象  缺点:无法对象识别,即所有对象都是object类型;方法内存空间浪费/封装不太完善
function sayname(){    //可以有效节省内存空间
  console.log(this.name);
}
function createobject(name, age, gender){
var obj = {
name:name,
age:age,
gender:gender,
sayname: sayname,    //将方法写在外面,可以有效节省内存空间
};
return obj;    //或者直接返回对象
}
 
var o1 = createobject('zhangsan', 12, 'man');
var o2 = createobject('lisi', 15, 'woman');
var dog = createobject('erha', 4, 'man');
console.log(o1, o2, dog);
//通过实例找构造函数
console.log(o1.constructor);     //object
 
②构造函数模式创建对象 
自定义构造函数     问题:方法内存空间浪费/封装不太完善
          
function sayname(){    //可以有效节省内存空间
  console.log(this.name);
}
function person(name, age, gender){
//this指向new关键字创建的实例
this.name = name;
this.age = age;
this.gender = gender;
sayname: sayname,    //将方法写在外面,可以有效节省内存空间
}
var p1 = new person("terry",11,"man");
console.log(p1)
console.log(p1.constructor);    //[function: person]
 
function dog(name, age, color){
//this指向new关键字创建的实例
this.name = name;
this.age = age;
this.color= color;
sayname: sayname,    //将方法写在外面,可以有效节省内存空间
}
var d1 = new dog("erha",2,"red");
console.log(d1)
console.log(d1.constructor);   //[function: dog]
 
③原型模式创建对象 
问题: 实例的数据隔离不安全,因为里面的数据共享
function person(){}
person.prototype.name = 'zhangsan';
person.prototype.friends = [];
person.prototype.sayname = function(){
  console.log(this.name);
};
var p1 = new person();
consoe.log(p1.name);    //zhangsan
var p2 = new person();
consoe.log(p1.name);    //zhangsan
p1.friends.push('terry');
console.log(p1.friends);  //['terry']
console.log(p2.friends);  //['terry']
console.log(p1.sayname === p2.sayname);   //true
 
④组合使用构造函数模式和原型模式 
//每个实例自有的放到构造函数中,实例共享的放到原型对象中
function person(name, age, gender){
//this指向new关键字创建的实例
this.name = name;
this.age = age;
this.gender = gender;
this.friends = [];
}
person.prototype = {    //实例共享的数据
constructor : person,
sayname:function(){
  alert(this.name);
       }
}
 
var p1 = new person("terry",11,"man");
console.log(p1);
console.log(p1.constructor);   //{function: person]
var p2 = new person("larry",11,"woman");
p1.friends.push('hello');
console.log(p1.friends);   //['hello']
console.log(p2.friends);   //[]
 
console.log(person('aaaa'))   //undefined, 因为this指针需要指向new关键字,这里只有person,没有new,所以它没有返回对象,返回的是undefined
 
28、对象深入了解
          ①可枚举性:
                    在打印一个对象,所能看到的属性,这些属性的可枚举性都是true;
                    for-in循环返回的属性,这些属性的可枚举性也都是true。
 
          ②对象的属性类型:
[[configurable]]: 表示是否通过delete删除属性从而重新定义属性,能否修改属性的特性,或者能否把属性修改为访问 器属性直接定义在对象中,默认为true)
 
[[enumerable]]: 表示能否通过for-in循环返回属性。(直接定义在对象中,默认为true)
 
[[wriable]]: 表示能否修改属性的值。(直接定义在对象中,默认为true)
 
[[value]]: 包含这个属性的数据值 name:jacky
 
          ③对象的属性特性
var obj = {
  name:'zhangsan',
  age:12,
};
console.log(obj); //{name:'zhangsan', age: 12,}
 
读取属性的特性 object.getownpropertydescriptor();获取指定属性的描述符该方法接受两个参数, 第一个为属性所在的对象,第二个为要读取其描述符的属性名称
 
//获取属性的描述信息
console.log(object.getownpropertydescriptor(obj, 'name'));   //{vale: 'zhangsan', writerable:true, enumerable:true, configurable: true}
 
要修改属性默认的特性,必须使用ecmascript5的object.defineproperty()方法 defineproperty(属性所在的对象,属性的名字,一个描述符对象);
 
//修改属性的描述信息
object.defineproperty(obj, 'name', {
//设置属性不可枚举
enumerable: false,   ------->console.log(obj);   //{age:12}
//设置属性不可修改
writable:false,             -------->obj.name = 'lisi'; console.log(obj.name); //zhangsan
//设置属性值
value:'terry',              --------->console.log(obj.name);     //terry
//设置属性是否可以删除delete,是否可以重新定义,是否可以配置
configurable:false,         --------->别人就不能改变这个属性
})
 
④访问器属性      没有值,有get方法和set方法, configurable的属性默认为false
var obj = {
  name:'zhangsan',
  age:12,
  _weight:100,
};
object.defineproperty(obj, 'weight', {
  get:function(){
    return this._weight-5;
  },
  set:function(param){
    this._weight = param
  },
  //enumerable:true,
});
/*object.defineproperty(obj, '_weight', {
  enumerable:false
});*/
console.log(obj.weight);   //95
obj.weight = 130
console.log(obj.weight);   //125
console.log(obj._weight);   //130
console.log(obj);  //   {name:'zhangsan', age: 12, weight: [getter|setter]}
                    console.log(object.getownpropertydescript(obj, 'weight'));
console.log(object.getownpropertydescript(obj, '_weight'));