javascript 学习笔记之面向对象编程

ECMA-262 把对象定义为:'无序属性的集合,其属性可以包含基本值,对象或者函数'。(参考资料javascript高级程序设计)
对象特殊属性:数据属性和访问器属性
1)数据属性:
[Configurable]-是否可删除  [Enumerable]-是否可枚举for in  [Writable]-是否可写  [value]值
要修改默认属性必须使用defineProperty(Object,key,descriptor)方法
例如:


var Person = {
		name:"john",
		age:"20",
		job:"student",
		sayName: function(){
			alert(this.name);
		}
		
	}
	Object.defineProperty(Person,"age",{
		configurable: false,
		enumerable: false,
		writable: false,
		value: 28,
	})
	console.log(Person.age);//28
	console.log(delete(Person.age));//不可删 false
	console.log(Person.age=20);
	Prson.age = 20;
	console.log(Person.age)//28,只读
定义多个属性	definePropertys(object,{
age:{
		value:23
	},
name:{
		configurable:false
	}
});
2)访问器属性:不包含数据,在读取时调用geter函数,写入时调用seter函数,该属性必须用defineProperty方法定义
如:
Object.defineProperty(Person,'name',{
    get:function(){
		return this.name;    
	},
	set:function(){
		
		console.log("修改");
	}
});
Person.name = "Li";//修改
读取特性:Object.getOwnPropertyDescriptor(object,"property")(..还好不常用);
*重点来了:*

1)创建对象

工厂模式:
function Person(name,age){
	var Object = new Object();
	Object.name = name;
	Object.age = age;
	
	Object.sayName = function(){
		console.log(this.name);
	}
	return Object;
}
var p1 =new Person("许涛",32);

构造函数模式:
var Person = function(name,age){
	this.name = name;
	this.age = age;
	
	this.sayName = function(){
		console.log(this.name);
	}
}
var p1 = new Person(name,age);
构造函数模式缺点:对象方法创建太多了影响性能,因为每个对象创建时都new
了一个方法

原型模式:
var Person = function(){};
Person.prototype.name = "马云";
Person.prototype.age = 11;
Person.prototype.sayName = function(){
	console.log(this.name);	
}
简写:
Person.prototype = {
	name:"马云",
	age:12,
	sayName: function(){
		console.log(this.name);
	}
}
var p1 = new Person();
原型模式缺点,每个对象实例属性一样
例如:
Person.prototype.friends =["许涛","马云","张三"];
var p2 = new Person();
//这里在p2实例中加了
p2.friends.push("John");
console.log(p1.friends);//["许涛","马云","张三","John"]


所以组合使用构造函数模式与原型模式可以有效避免缺点,集二者之长(使用最多):
function Person(name,age){
	//这里使用构造函数模式定义属性
	this.name = name;
	this.age = age;
	this.friends = ["John","Li"];
	
}
//把方法写在原型链中,所有实例共享
Person.prototype = {
	sayName: function(){
		console.log("this.name");
	}
}
var p1 =new Person("peter",32);
var p2 = new Person("安琪",18);
p2.friends.push("peter");
console.log(p1.friends);//['john','li'];
console.log(p2.friends);//[...'peter'];
还有其他自定义模式都是基于前三种模式进化出来的。。

2)继承

原型链继承:
function Person(){
	this.type = "man";
}
Person.prototype.sayType = function(){
    console.log("my name is: "+this.type)
}
//子对象
function Student(){
	this.job = "student";
}
//继承
Student.prototype =new Person();
var xiaoming = new Student();
console.log(xiaoming.type);
缺点:属性共享问题
Person.prototype.hairs =["black","green","yellow"];
var stu1 = new Student();
var stu2 = new Student();
stu2.hairs.push("blue");
console.log(stu1.hairs,stu2.hairs);

//构造函数继承:
//子对象
function Chinese(){
	//继承 通过call调用Person方法
	Person.call(this);
	this.country = "China";
	
}
var c1 = new Chinese();
console.log(c1.type);//man

//组合继承:(常用)
//这里新创建一个People对象作为父对象
function People(name){
	this.name = name;
		
}
People.prototype.sayName = function(){
	console.log(this.name);
	return this.name;
}
//子对象
function Man(name){
	People.call(this,name);
}
Man.prototype = new People();
Man.prototype.constructor = Man;
var man1 = new Man();
console.log(man1.name);
console.log(man1.sayName());
//缺点:无论何时都要调用两次父类

//原型式继承
//这里定义一个object方法用作原型继承返回一个子实例
function object(SuperObject){
	function F(){};
	F.prototype = SuperObject;
	return new F();
}//es5 新增Object.create()方法与object()方法一样
//寄生式继承 相当于对object进行扩展
function clone(o){
	var clone = object(o);
	//添加新方法
	clone.sayHi = fuction(){
		alert("Hi");
	}
	return clone; 
}
//寄生组合式继承
function iher(subType,superType){
	var prototype = object(superType.prototype);
	prototype.constructor = subType;
	subType.prototype = prototype;
}
//实例
function SuperType(name){
	this.name = name;	
}
SuperType.prototype.sayName = function(){
	console.log(this.name);	
}
//子对象
function SubType(name,age){
	SuperType.call(this,name);
	this.age = age;
}
//不用两次调用父类了
iher(SubType,SuperType);
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值