原型继承
function Father(name="李四",age=20) {
this.name = name;
this.age = age
}
Father.prototype.gender = "男"
function Child() {
this.name = "张三"
}
Child.prototype = new Father()
var child = new Child()
child.gender="女"
child.age = 18
console.log("child instanceof Father",child instanceof Father) // true
console.log("child",child)
// 缺点1:子类不可以向父类传参, 缺点2:子类的实例共享了父类引用类型,如果父类该变子类也会变化
构造函数继承
// 构造函数继承,在子类的构造函数中执行父类构造函数,同时通过call该变这个this指向,为子类的实例
function Father(name="李四",age=20) {
this.name = name;
this.age = age
}
Father.prototype.gender = "男"
function Child(name) {
Father.call(this,name);
}
var child = new Child("张三")
console.log("child.name",child.name)
console.log("child.age",child.age)
console.log("child instanceof Father",child instanceof Father) // false
console.log("child.gender",child.gender) // null
// 优点:可以向父类传参;
// 缺点:只是继承了父类的实例属性,没有继承父类原型上的属性和方法
寄生式继承
// 寄生式继承 思路和原型式继承一脉相承,创建一个用于封装继承过程的函数
function object(o) {
function F() {}
F.prototype = o;
return new F();
}
function createPerson(obj) {
var clone = object(obj);
clone.sayName = function() {
console.log("name")
}
return clone
}
var person = {
name: '张三',
friends: ["李四","王五"]
}
var person1 = createPerson(person)
person1.sayName() // name
// 缺点没有解决引用的问题,引用类型值还是共享的
组合继承
// 组合继承(借用原型链继承和构造函数继承)
function Father(name="李四",age=20) {
this.name = name;
this.age = age
}
Father.prototype.gender = "男";
function Child(name) { // 在子类的构造函数里边执行父类,该变父类的this指向
Father.call(this,name)
}
Child.prototype = new Father(); // 让子类的实例等于父类的原型
var child = new Child("张三")
console.log("child.name",child.name)
console.log("child.age",child.age)
console.log("child instanceof Father",child instanceof Father) // true
console.log("child.gender",child.gender) // 男
// 优点:子类可以向父类传参;每个新实例引入的构造函数属性都是私有的不共享父类引用属性
// 缺点:调用了两次构造函数(消耗内存),子类的构造函数会替代原型上的那个父类的构造函数
寄生组合继承
// 寄生组合继承
function Father(name="李四",age=20) {
this.name = name;
this.age = age
}
Father.prototype.gender = "男";
function Child(name) { // 在子类的构造函数里边执行父类,该变父类的this指向
Father.call(this,name)
}
Child.prototype = Object.create(Father.prototype) // 让子类的实例等于父类的原型
Child.prototype.constructor = Child;
var child = new Child("张三")
child.gender = "女"
console.log("child.name",child.name)
console.log("child.age",child.age)
console.log("child instanceof Father",child instanceof Father) // true
console.log("child.gender",child.gender) // 男
console.log("child222",Father.prototype)
// 优点就是解决了调用两次构造函数
es6的class继承
class Person {
constructor(name="李四",age="18") {
this.name = name;
this.age = age
}
}
Person.prototype.gender = "男"
class Child extends Person {
constructor(name) {
super(name)
this.name = name
}
}
var child = new Child("张三")
child.age = 20
child.gender = "女"
console.log("child instanceof Person",child instanceof Person) // true
console.log("child",child)
|