配合下面解释再看例子
function Person(name){//形参用来接受实例传过来的实参
this.name = name;
}
Person.prototype.showName = function (){
console.log(this.name);//person1打印hello person2打印world
}
var person1 = new Person('hello');
person1.showName();
var person2 = new Person('world');
person2.showName();
构造函数
- 函数名首字母大写
function Person(){}
- 这是为了区别于普通的函数,构造函数本身其实就是普通的函数,只是我们专门用它来实现了构造的功能,所以专门起了一个名字叫构造函数,任何函数都可以成为构造函数,这取决于你调用函数的方式,当使用了New的方式调用就成了构造函数。
new 关键字调用
- 当用New去调用一个函数的时候,this的指向会不一样。
- 每new一次,系统都会新创建一个内存,这两个对象各自有各自的内存空间,但他们具有相同的功能,还不共用。
- showName()方法是共享的,也就是说他们共用一个内存,更进一步的说它们存在引用关系。
- 所以我们可以把可以共享复用的方法放在函数的
prototype上,不想共享的可以通过构造函数new来调用。
prototype
1.每个函数都有一个
prototype属性,他被称为原型对象;
- 我们可以通过
Person.prototype.showName把方法和属性写在它上面;
- 而通过
var person = new Person('hello')这个函数创建出来的实例对象,都能共享这个原型对象下的方法和属性;
_proto_
- 每个实例化对象都有
_proto_属性,它是一个指针,指向函数的prototype,也就是保存了它的地址。有了地址就能找到对象。
- 调用
person2.__proto__属性,保存了构造函数的原型对象的地址,通过这个属性就可以拥有原型对象下的所有属性和方法,_proto_属性实际就是实例化对象和原型对象之间的连接
原型链
- 所有的函数都有
prototype属性,它指向原型对象;prototype是一个对象,浏览器默认给他开辟堆内存
- 每一个函数的原型对象都有的默认属性
constructor指向当前类的本身
- 每一个实例(对象),都有一个
__proto__属性,指向所属类的原型
Person.prototype == person1.__proto__ //true
Person.prototype.constructor == person1.__proto__.constructor //true
Person.prototype.constructor.__proto__ == person1.__proto__.constructor.__proto__ //yrue
Person.prototype.__proto__ == Object.prototype //true
Person.prototype.__proto__ == Function.prototype.__proto__ //true
Function.prototype.__proto__ == Object.prototype //true