JS面向对象
1. 创建对象
- 字面量创建
var people={
name:"iwen",
age:30,
eat:function(){
alert("能吃");
}
}
people.eat();
- new/原型链创建
function People(){
}
People.prototype={
name:"iwen",
age:30,
eat:function(){
alert("能吃");
}
}
var p=new People();
p.eat();
- return
function Person(name)={
var _this={}
_this._name=name;
_this.eat=function(){
alert(_this.name+"能吃");
}
return _this;
}
- Object.create
var obj=Object.create({x:1});
obj.x;//1
2. 对象继承
function People(){
}
People.prototype.eat=function(){
alert("能吃");
}
function Student(){
}
Student.prototype=new People();
var stu=new Student();
stu.eat();
///
function Person(name){
var _this={}
_this._name=name;
}
return _this;
}
function Student(name){
var _this=Person;
return _this;
}
//
function Person(){
}
function Student(){
}
Student.prototype = Object.create(Person.prototype);
Student.prototype.constructor=Student;
如果子类也有一个eat()Student.prototype.eat=function(){alert("学生能吃")}
则只调用子类的方法;可以通过var SuperSsay=Student.prototype.say
,然后在子类方法中加上SuperSsay.call(this)
来调用父类的同名方法。
3. 对象封装
(function(){
function Student(name){
this._name=name;
}
Student.prototype=new People();
var stu=new Student();
window.Student=Student;
}())
4.原型链
function foo(){
foo.prototype.z=3;
}
var obj=new foo();
obj.x=1;
obj.y=2;
obj.x;//1对象属性有
obj.y;//2对象属性有
obj.z;//3对象属性没有,则查找对象的原型链
obj.hasOwnPrototype('z');//false 因为原型属性没有'z'
obj.z=5;//因为原型没有属性z,所以会在原型上新建一个属性z=5,对原型链上的属性z没影响
delete obj.z;//true 并删除原型上的属性z,不能删除原型链上的属性z
obj.z;//3
//如果使用Object.create方法创建对象
var obj=Object.create({x:1});
obj.x;//1
obj.hasOwnPrototype('x');//false,是因为obj的原型链指向{x:1}这个对象,x是原型链中的属性,obj的原型里面并没有这个属性
对象有__proto__属性,函数有prototype属性,函数也是一个对象所以函数也有__proto__属性,而对象的__proto__属性指向构造这个对象的函数的函数原型,即
function obj(){}
var o=new obj();
console.log(o.__proto__===obj.prototype);//true
函数的__proto__属性指向构造这个函数的函数的原型,比如函数是像function a(){}
这样定义的则a.__proto__===Function.prototype
,如果函数是像var a={}
,或者var a=new Object()
等方法定义的,则a.__proto__===Object.prototype
。
函数的原型即prototype属性包含constructor属性,指向函数本身,即obj.prototype.constructor===obj
。浏览器中还包含一个__proto__属性(Object.prototype.__proto__)
但不推荐使用