zoukankan      html  css  js  c++  java
  • 对于JavaScript的__proto__以及prototype与constructor的理解。

    js是一门有趣的语音,最近一直在学习中,看了不少书籍。对于对象的一些内置特性了解的不好。

    这里写一些简单的笔记,方便自己的学习

    首先我自己的理解,这里面由三个对象,一个是实例,一个是构建函数,还有一个是原型。

    实例可以用过__proto__查看自己的原型或者用Object.getPrototypeOf这个命令查看,一样的效果

    function Demo(a){this.a = a}
    undefined
    var d = new Demo(99)
    undefined
    d.__proto__
    {constructor: ƒ}
    Object.getPrototypeOf(d)
    {constructor: ƒ}
    Demo.prototype
    {constructor: ƒ}
    

     从代码可以看出,实例可以通过__proto__查看自己的原型,这个原型可以理解为Python中的类?(也不是很对)

    后续通过原型给实例添加一些属性与方法,比较像Python中的猴子补丁。

    不光从实例可以看到原型,也可以通过构建函数查看原型,实例可以通过constructor查看构建函数。

    d.constructor === Demo
    true
    d.constructor
    ƒ Demo(a){this.a = a}
    Demo
    ƒ Demo(a){this.a = a}
    

     既然可以看到构建函数,我们通过构建函数查看一下原型

    Demo.prototype
    {constructor: ƒ}constructor: ƒ Demo(a)__proto__: Object
    d.__proto__
    {constructor: ƒ}constructor: ƒ Demo(a)__proto__: Object
    Demo.prototype === d.__proto__
    true
    

     通过演示,可以直接通过实例查看原型,也可以通过构建函数查看原型。原型有什么用,他可以在添加公用的属性与方法。

    Demo
    ƒ Demo(a){this.a = a}
    Demo.prototype.show = function(){console.log('show'+this.a)}
    ƒ (){console.log('show'+this.a)}
    d.show()
    VM8836:1 show99
    

     这里面肯定有人说,可以在构建函数的地方直接定义 添加这个对象属性。

    function Demo(a){
      this.a = a;
      this.show = function(){console.log('show'+this.a)}
    }
    

     但这样的话,会在每个新建的实例创建一个这个的方法,非常浪费内存空间。

    所以方法在原型中添加更加合适,为什么的话,看我下面分析

    function Demo(a){
      this.a = a;
      this.show = function(){console.log('show'+this.a)}
    }
    undefined    
    Demo.prototype
    {constructor: ƒ}constructor: ƒ Demo(a)__proto__: Object
    Demo.prototype.show
    undefined
    

     上面的代码可以看出在构建函数内通过prototype并不能查看到原型内的一些提供给实例的公用方法或者属性,

    其实也对,因为在构建函数里面定义的属性与方法每个实例都是特有的。

    所以这样的话,如果想使用构建函数内定义的方法会比较麻烦,只能通过实例来调用改方法。

    但如果通过原型的方式,给原型赋值属性并添加方法的方式,可以通过原型调用该方法,通过call、apply、bind的方式或者指定调用的方式来调用该方法,而且同样实例也能使用该方法。

    Demo.prototype.show = function(){return this.a + 'hello' + this.b}
    ƒ (){return this.a + 'hello' + this.b}
    d.show()
    "99helloundefined"
    Demo.prototype.show.call({a:888,b:'xxx'})
    "888helloxxx"
    var a = 'main'
    undefined
    var b = 'window'
    undefined
    var show = Demo.prototype.show  //赋值到全局变量组
    undefined
    show()
    "mainhellowindow"
    

    最后来看一下原型函数,通过constructor来获取,实例与原型的constructor调用都返回原型函数

    d.constructor === Demo
    true
    Demo.prototype.constructor ===Demo
    true
    

    最后是我前面碰到疑惑的,就是通过函数去调用__proto__获取构建函数的原型,以及constructor获取构建函数。

    Demo.__proto__
    ƒ () { [native code] }
    Demo.constructor
    ƒ Function() { [native code] }
    Demo.__proto__.parent_show = function(){console.log(this.a)}
    ƒ (){console.log(this.a)}
    

     通过__proto__可以查看到构建函数的原型,也可以通过构建函数给原型给构建函数添加共有属性方法,

    通过constructor可以看出构建函数的构建函数,正是Function函数。

    后续还有继承,下次有空再写笔记,继续主要通过__proto__查看上级的原型,实例继承该原型的属性以及方法。

    记住,任何一个函数都有prototype属性,这个属性是拿来给下级的实例调用的,所有的对象都继承或者实例来至Object函数

    所以Object中的原型属性,每个对象都会拥有。

  • 相关阅读:
    Java实现 蓝桥杯VIP 算法提高 阮小二买彩票
    Java实现 蓝桥杯VIP 算法提高 传染病控制
    Java实现 蓝桥杯VIP 算法提高 传染病控制
    Java实现 蓝桥杯VIP 算法提高 传染病控制
    Java实现 蓝桥杯VIP 算法提高 传染病控制
    Java实现 蓝桥杯VIP 算法提高 传染病控制
    Java实现 蓝桥杯VIP 算法提高 企业奖金发放
    Java实现 蓝桥杯VIP 算法提高 企业奖金发放
    让程序后台隐藏运行
    只要你喜欢,并且可以养家糊口,就是好的
  • 原文地址:https://www.cnblogs.com/sidianok/p/13263130.html
Copyright © 2011-2022 走看看