• javascript之原型(prototype)


    一、由来

    1. 当初在设计javascript时不想引入类的概念,但要实现类的功能。借鉴了高级面向对象语言中,创建一个实例时,其实就是执行了该类的构造函数,因此,作者用   new + 构造函数  的形式来表示生成的实例。这里提到的构造函数其实就是我们平时常见到的普通函数,只是为了区分,首字母大写。
    2. 还有一个问题:这样创建出来的实例,来自同一个“类”,但却不知道,这时提出了prototype的概念,用来存放该实例的构造函数。
    3. 除了通过bind绑定的没有,每个函数都有prototype属性,prototype属性包含了contructor和在构造函数中定义的所有属性和方法。其中,contructor是真正存放该实例的构造函数的地方。

    二、与constructor的关系

      其实真正存放实例的构造函数是在constructor,constructor指向构造函数,constructor又是prototype的属性,prototype还是构造函数的属性。是不是乱了,反正我是傻了~~

      

    三、prototype 和 __proto__ 区别:

      构造函数对应的是prototype,实例对象对应的是_proto_,两者都是相同的,都指向构造函数的原型。 

      例子:

    function Demo(){
                this.name = "demo";
            }
    
            const demo = new Demo();
    
            console.dir(Demo.prototype);
            console.dir(demo.__proto__);
            console.log(Demo.prototype == demo.__proto__);
    

      

     四、相关的方法

      1.判断实例的构造函数:Object instanceof Function    和    Function.prototype.isPrototypeOf(Object)

      例如:

            function Demo(){
                this.name = "demo";
            }
    
            const demo = new Demo();
    
            console.log(demo instanceof Demo);
            console.log(Demo.prototype.isPrototypeOf(demo));
    

      

     2.检测属性来着与实例还是原型:hasOwnProperty()

    例如:

    function Demo(){
                this.name = "demo";
            }
            Demo.prototype.age = 11;
    
            const demo = new Demo();
            console.dir(demo.name+'.....'+demo.hasOwnProperty('name'));     //demo.....true
            console.dir(demo.age+'.....'+demo.hasOwnProperty('age'));       //11.....false
    

    五、易混的概念

    难点:

    (1)函数即对象

    在JS里,函数就是Function函数的实例对象,函数即是对象。

    function Fun(){
                console.log('fun');
            }
            const fun1 = new Fun();         //对象由函数创建
            console.log(Fun.constructor);      //Function   结论:Fun 的构造函数是 Function
            console.log(Function.constructor);       //Function       结论:Function 的构造函数还是是 Function
            console.log(Object.constructor);        //Function       结论:Object 的构造函数还是是 Function
            //结论:对象由函数创建,函数都是Function函数的实例对象,也就是函数即对象

    (2)constructor 的理解

     一个拿来保存自己构造函数引用的属性。由于同一个构造函数生成的实例的constructor 值的一样,为了节省内存空间,constructor被当成共享属性,存放在prototype(下文会介绍到)中。

    (3)prototype 的理解

    目的:为了内存着想,专门存放共享属性和方法的地方。 在自身存放在这些实例的构造函数上。又称为原型对象。

    function Foo(){
                console.log('Foo');
            }
    
            const foo1 = new Foo();            //Foo
            const foo2 = new Foo();            //Foo
            //两个实例添加相同作用的方法
            foo1.say = function(){
                console.log('hello!!!');
            }
            foo2.say = function(){
                console.log('hello!!!');
            }
            console.log(foo1.say === foo2.say);        //false     //尽管二者的代码相同,但在我们的内存里,却存放了两份一模一样的东西,造成内存的浪费
    
            //prototype的好处:
            Foo.prototype.show = function(){
                console.log("This is a show function");
            }
            foo1.show();        // This is a show function
            foo2.show();        // This is a show function
            console.log(foo1.show === foo2.show);            //true         //这时,内存的存储空间也是相同的,没有造成浪费

    (4)__proto__属性

    目的:让实例能找到自己的原型对象

    特点:只要是对象就会有__proto__属性

    (5)原型链

     __proto__ 把原型对象和实例串起来的的形式,就是原型链

    六、查阅的资料

    1. 阮一峰的网络日志
    2. 神秘者007-简书
    3. 用自己的方式(图)理解constructor、prototype、__proto__和原型链

  • 相关阅读:
    拓端tecdat|R语言JAGS贝叶斯回归模型分析博士生延期毕业完成论文时间
    拓端tecdat|数据感知游客的森林公园游憩需求
    空间100%
    uniq -c 去掉重复行
    工作中实用的Shell脚本实例
    Linux下如何解压和压缩rar格式的包
    LRM-00109: could not open parameter file
    Xmanager5 Passive oracle图形化界面出来之后鼠标点不了
    谷歌浏览器请求返回JSON内容自动格式化
    JENKINS中创建全局变量并在JOB中使用
  • 原文地址:https://www.cnblogs.com/zxn-114477/p/14211035.html
Copyright © 2020-2023  润新知