javascript - 经典继承的一个疑问
高洛峰
高洛峰 2017-04-11 09:58:10
[JavaScript讨论组]
<script>
    function Animal(age)
    {
        this.age = age;
    }
    Animal.prototype = {
        constructor:Animal,
        bark:function(){
            alert(this+'is barking');
        }
    }
    //....
    function extend(){
            var F = new Function();
            F.prototype = Animal.prototype;
            Dog.prototype = new F();
            //还原子类构造器
            Dog.prototype.constructor = Dog;
        };
    extend();
    function Dog(sex,age)
    {
        this.sex = sex;
        Animal.call(this,age);

        
    }
    dog = new Dog('boy','23');
    console.log(dog.sex + dog.age );
    dog.bark();
</script>

此处的代码为什么要生成 F这一个空函数作为一个临时中转,不直接使用 Dog.prototype = Animal.prototype呢?

高洛峰
高洛峰

拥有18年软件开发和IT教学经验。曾任多家上市公司技术总监、架构师、项目经理、高级软件工程师等职务。 网络人气名人讲师,...

全部回复(5)
PHP中文网

你直接把Dog.prototype = Animal.prototype,这时假如我的Dog.prototypeAnimal.prototype指向的是同一片内存,那么就意味着一个改变就会影响另外一个,所以采取这种方式,为Dog.prototype重新开辟内存。

大家讲道理

关于js的继承,实现的方式有几种,最好不要去对应面向对象诸如Java,C#之类的继承(而且,现在很多的前端框架都在弱化继承,因为js是基于原型的)。

我也写过一个js的继承(部分代码):

pm.extend=function(sp,ext){
    //
    if(!utils.isFunction(sp)){
        
        return utils.extend.apply(this,slice.call(arguments,0));
    }
    var F=function(){
        
        //call the constructor
        F.superclass.constructor.apply(this,slice.call(arguments,0));          
    };
    
    //
    F.prototype=new sp();
    //
    utils.extend(F.prototype,ext);
    //
    F.prototype.constructor=sp;
    
    sp=ext.constructor !=ObjectProto.constructor ? ext.constructor : sp.prototype.constructor;
    F.superclass=sp.prototype;
    if(F.prototype.constructor === ObjectProto.constructor){
        
        F.prototype.constructor=F;
    }
    
    return F;
};

js的继承会导致出现几个问题,constructor改变,prototype指向出现问题,通过instanceof得不到你想要的继承关系等。

你这里,那个F函数就是为了解决prototype指向的问题的(可以看看相关的书籍,在这里推荐一下月影的《JavaScript王者归来》)

对于js的继承这个东东,建议还是停留在学习,了解上,可以看看一些常见的面向对象的js的设计,比如Extjs(这个用于学习js相关的很有用),Dojo等。

PHP中文网

如果父子的 prototype 都指向一个相同的对象,如果子对象的 prototype 的属性被修改,那么就会影响到父对象。所以用一个中介 new F() 来改变这个情况。

PHP中文网

直接使用 Dog.prototype = Animal.prototype
这样的话,Dog.prototype更改了,则会引起Animal.prototype更改,这肯定不合你的要求吧?

ringa_lee

现在也可以使用Object.create实现继承,dog.prototype=Object.create(animal.prototype)不会造成dog.prototype和animal.prototype指向同一片内存的情况。

热门教程
更多>
最新下载
更多>
网站特效
网站源码
网站素材
前端模板
关于我们 免责申明 举报中心 意见反馈 讲师合作 广告合作 最新更新 English
php中文网:公益在线php培训,帮助PHP学习者快速成长!
关注服务号 技术交流群
PHP中文网订阅号
每天精选资源文章推送
PHP中文网APP
随时随地碎片化学习

Copyright 2014-2025 https://www.php.cn/ All Rights Reserved | php.cn | 湘ICP备2023035733号