js实现继承

一、原型继承

            function Father(lastname,sex){
                this.lastname=lastname;    //
                this.sex=sex;//性别    
            }
            //父类原型属性
            Father.prototype.xo='xxx';
            
            //子类
            function Son(firstname){
                this.firstname=firstname;//
            }
                    
            Son.prototype=new Father('杨'); //原型继承,son的原型已经指向了father对象的实例
            
            var son =  new Son('清');
            alert(son.firstname);//
            alert(son.lastname);//杨  继承的属性
            alert(son.xo);//xxx  继承的原型属性
            alert(son.sex);//undefined//继承时未传值

缺点:继承后还必须给父类传参, new Father('杨'), 不能把参数直接传入子类中

二、借用构造函数继承

            //父类
            function Father(lastname,sex){
                this.lastname=lastname;    //
                this.sex=sex;//性别    
            }
            //父类原型属性
            Father.prototype.xo='xxx';
            
            //子类
            function Son(lastname,firstname){
                Father.call(this,lastname);//将Father构造函数绑定到Son
                this.firstname=firstname;//
            }
                
            var son =  new Son('杨','清');
            alert(son.firstname);//
            alert(son.lastname);//杨  继承的属性
            alert(son.xo);//undefined  未能继承到原型属性
            alert(son.sex);//undefined//不需要继承属性

缺点:未能继承到原型属性

三、 组合继承(原型继承+借用构造函数继承)

            function Father(lastname,sex){
                this.lastname=lastname;    //
                this.sex=sex;//性别    
            }
            //父类原型属性
            Father.prototype.xo='xxx';
            
            //子类
            function Son(lastname,firstname){
                Father.call(this,lastname);//借用构造函数继承
                this.firstname=firstname;//
            }
            Son.prototype=new Father(); //原型继承,不用传参 只为继承原型属性
            var son =  new Son('杨','清');
            alert(son.firstname);//
            alert(son.lastname);//杨  继承的属性
            alert(son.xo);//xxx  继承到原型属性
            alert(son.sex);//undefined//不需要继承属性

缺点:虽然原型继承时new Father()没有传入参数,还是又继承了一次Father的模板

四、 组合继承(最终版)

            var __extends = this.__extends || function (sub, sup) {
            for (var p in sup) if (sup.hasOwnProperty(p)) sub[p] = sup[p];//继承父类自身属性
            function __() { this.constructor = sub; } //创建一个空函数 并将构造指向子类
            __.prototype = sup.prototype;//空函数原型指向父类原型
            //以上代码 创建出了一个空函数 1.无属性模板。2.构造函数是子类。3.原型是指向父类原型
                
            sub.prototype = new __();//改变原型对象, 指向空函数
            sub.superClass =sup.prototype;//保持父类原型    
            if(sup.prototype.constructor==Object.prototype.constructor){
                    //如果简单原型覆盖 则手动添加
                    sup.prototype.constructor=sup;
                }
            };
                        
            function Person(name,age){
                this.name=name;
                this.age=age;    
            }
            Person.ff='sssc';
            
            Person.prototype={
                sayName : function(){
                    alert(this.name);    
                }             
            }
                                    
            function Boy(name ,age,sex){    
                Boy.superClass.constructor.call(this,name,age);
                Person.call(this,name,age);
                this.sex=sex;
            }
            __extends(Boy,Person);//继承
            var b=new Boy('对对',23,'男');
            alert(b.name);
            alert(b.age);
            alert(b.sex);            
            b.sayName();
            alert(Boy.prototype.constructor.ff);//输出父类自身属性
原文地址:https://www.cnblogs.com/yangjingqi/p/4339592.html