for (var i in p) :遍历p数组。
对原型链的理解:作用是实现继承。让一个对象的原型等于另一个对象的实例。subType.prototype = new superType();
对继承的理解:利用构造函数继承属性,利用原型链继承方法。
继承分两种:接口继承,实现继承。
注:js创建函数
1、函数声明 function tfs(){};
2、构造函数 var tfs =new Tfs();
3、函数字面量var tfs = function(){};
点击打开链接
1、原型链。
接口继承:只继承方法签名。(方法签名:方法名和参数列表 Log.log(String message, Exception e, Object... objects) {...})
实现继承:继承实际的方法。
ECMAscript只支持实现继承,原因:js函数没有签名。(因为js的参数是由包含0或者多个值的数组来表示的。它所谓的命名参数只是提供便利,但不是必须的。
在其他语言中,命名参数这块必须要求事先创建函数签名,而将来的调用也必须与该签名一致。js没有这些条条框框,解析器不会验证命名参数,所以说js没有签名。譬如
function sayHello () {
alert("Hello" + arguments[0] + ", " + arguments[1]);
}
sayHello ("baby", "how are you?");
这个例子很明显了。命名参数为空,而我们照样可以按照两个参数的格式去调用该方法。所谓的参数类型,参数个数,参数位置,出入参数,js统统不关心,它所有的值都被放到arguments中了。需要返回值的话直接return,不用声明。
),另,其实现继承主要依靠原型链实现。
构造函数,原型,实例的关系:
每个构造函数都有一个原型对象,每个原型对象都有一个指向构造函数的指针,实例都包含一个指向原型对象的内部指针。
确定原型和实例的关系:两种方法:instanceof操作符,isPrototypeOf()方法
1、alert(instance instanceof Object); //true
2、alert(Object.prototype.isPrototypeOf(instance)); //true
注:不能使用对象字面量创建原型方法,可能会重写原型链。如:
应该:
原型链的问题?为什么不单独使用原型链?‘
1、只能在构造函数里定义属性,而不能在原型对象里定义属性。
2、在创建子类型的实例时,不能向超类型的构造函数中传递参数。(
A类 继承了 B类的属性,那么B就是A的超类,也叫父类。)
2、借用构造函数。
基本思想:在子类型构造函数内部调用超类型构造函数。(函数:特定环境下执行代码的对象)
![](https://img-blog.csdn.net/20170224204519280?watermark/2/text/aHR0cDovL2Jsb2cuY3Nkbi5uZXQvbWVsb2R5X2RheQ==/font/5a6L5L2T/fontsize/400/fill/I0JBQkFCMA==/dissolve/70/gravity/Center)
缺点:方法都在构造函数里定义,函数复用无从谈起。
3、组合继承。
基本思想:使用原型链实现对原型属性和方法的继承,通过借用构造函数来实现对实例属性的继承。
我的理解是:借用构造函数继承和定义属性,使用原型链定义和继承方法。
function superType(name){
this.name = name;
}
superType.prototype.sayName = function(){
alert(this.name);
}
function subType(name,age){
superType.call(this,name); //借用构造函数继承属性
this.age = age;
}
subType.prototype = new superType(); //使用原型链继承和定义方法
subType.prototype.constructor = SubType;
subType.prototype.sayAge = function(){
alert(this.age);
}
var instance1 = new subType("tfs",18);
instance1.name.push("tfr");
instance1.sayName(); //"tfs,tfr";
var instance2 = new subType("ft",17);
instance2.sayName(); //"ft";
4、原型式继承
目标:在不创建构造函数时,只想让一个对象和另一个对象保持类似时,用原型式继承。
浅复制:
function object(o){
function f(){}
f.prototype = o;
return new F();
}
5、寄生式继承
思想:创建一个仅用于封装继承过程的函数。该函数在内部以某种方式来增强对象,最后返回对象。
6、寄生组合式继承
为了改进组合继承两次调用
SuperType()
function superType(name){
this.name = name;
}
superType.prototype.sayName = function(){
alert(this.name);
}
function subType(name,age){
superType.call(this,name); //第二次调用SuperType()
this.age = age;
}
subType.prototype = new superType(); //第一次调用SuperType()
subType.prototype.constructor = SubType;
subType.prototype.sayAge = function(){
alert(this.age);
}
寄生组合继承基本模式:
function inheritPrototype(subType,superType){
var prototype = Object(subType,superType); //创建超类型一个副本
prototype.constructor = subType; //为创建的副本添加constructor属性
subType.prototype = prototype; //将副本赋值给子类型的原型。
}
上段代码变为:
function superType(name){
this.name = name;
}
superType.prototype.sayName = function(){
alert(this.name);
}
function subType(name,age){
superType.call(this,name);
this.age = age;
}
inheritPrototype(subType,superType);
subType.prototype.sayAge = function(){
alert(this.age);
}