• 理解JavaScript原型和原型链


    理解JavaScript原型和原型链 (资料整理,个人学习)

    (原文链接https://www.cnblogs.com/piaobodewu/p/13795077.html)

    精典图

     注意:

    (prototype-原型, _proto_-继承)

    1:只有Functions集合中的function有prototype属性。

    2:function的prototype指向Prototypes集合中的实例。

    3:Prototypes集合中的实例constructior属性指向Functions集合中的function。

    4:(new xx())对象中有_proto_属性。

    5:(new xx())对象_proto_指向Prototypes集合中的实例

    6:Functions集合中的function在new 的同时都继承(_proto_)同一个Prototypes集合中的function的实例。

    一切起源于null

     机器1号可不得了,它是JS世界的第一个对象,它是真正的万物始祖。它拥有的性质,是所有的对象都有的。
    __proto__是什么呢?是“生”的意思,或者换成专业点的叫法“继承”.

    有中生有

    一生二,二生三,三生万物

     通过object创造对象,Object制造对象时候,需要有一个模版,现在只有机器1号,它就取了机器1号当模版。图中的prototype就代表模板对象。

    通过new命令。按下“new”按钮,新的对象就造出来了。var obj = new Object();

     Object通过(prototype)模板创造new对象,对象通过(_proto_)继承模板,

     有生万物

    (注:__proto__[p]来代替)

     Object也指向了机器2号,这是因为机器2号是负责造对象的,当然也负责造Object对象

    Object有自己的模板:机器1号。而String、Number、Boolean、Array它们有模板吗?

    其实机器2号在创建它们的时候并不是直接创建它们的,而是先创建了对应对象的机器作为模板,然后再由各自的机器来创建它们。

    机器2号总体负责制造所有的对象,包含Object、String、Number、Boolean、Array,甚至还有之后的Function。当然它只是负责制造,并不一定会亲手去制造对象,可以通过制造对应的机器来帮助它制造对象

    • 机器1号制造了机器2号,机器2号总体负责各种对象的制造
    • 但是机器2号并不是直接造各种对象,而是通过先建造对应的机器(模板),再由对应的机器来制造对象(继承)。如:对于String,机器2号先制造了机器String号,然后由机器String号来制造String,机器2号只负责总体控制
    • 虽然机器2号制造了各种各样的机器,但是因为机器2号是由机器1号制造的,所以这些被制造的机器所属权还是归于机器1号的,毕竟机器1号是始祖级的。
    • 对象和对应的机器,通过prototype来连接。如:对于String,机器2号String通过prototype连接
    • 每个机器都有且只有一个的对象,每个对象也都有且只有一个机器作为模板

    万物缺活力-Function的制造

    • 它是由机器2号亲手制造的,所以它们之间有prototype相连
    • 而机器2号又是制造所有对象的负责者,所以它们之间有__proto__相连
    • Function.__proto__ === Function.prototype

    • 机器1号 = Object.prototype(机器1号是Object的模板)
    • 机器2号 = Function.prototype(机器2号是Function的模板)
    • 机器String号 = String.prototype(机器String是String的模板)
    • Function对象作为一个函数,就会有prototype属性,该属性将对应”function () {}”对象。
      Function对象作为一个对象,就有__proto__属性,该属性对应”Function.prototype”,
    • 也就是说,”Function._proto_ === Function.prototype”。

    世界动起来

    刚造出来的Function机器很难用,用法就像下面这个

    let Foo = new Function("name", "console.log(name)");

    Foo('dellyoung'); // 控制台打印出:dellyoung

    语法糖

    function Foo(name) { console.log(name); }

    Foo('dellyoung'); // 控制台打印出:dellyoung

    以造Foo()为例,于是JavaScript的世界的变成了下面的样子:

    • 机器Foo()号 = Foo.prototype
    • [p] = __proto_

    Function这个对象比较特殊,它new出来后,就是一个全新的对象了,function Foo()(注意:它等价于 let Foo = new Function())和ObjectStringNumber等这些对象一样,都是对象。

    既然都是对象,当然function Foo()也是由机器2号来控制制造的,但是机器2号很忙,它没有精力直接制造function Foo(),机器2号是通过制造出一个制造function Foo()的机器来制造function Foo()

    咱们称制造function Foo()的机器机器Foo()号

    当然既然是机器,所以机器Foo()也是机器1号控制的

    回到现实

     

     可以被用来new的对象或函数,我们都可以称之为构造函数,每个构造函数都和它的机器(也就是XXX.prototype)通过constructor相连,我们来画出构造函数和它们的constructor

     

    正式的语言总结一下就是:?

    • 子类的__proto__属性,表示构造函数的继承,总是指向父类。
    • 子类prototype属性的__proto__属性,表示方法的继承,总是指向父类的prototype属性。
    • 原型也是一个对象,通过原型可以实现对象的属性继承
    • 对于所有的对象,都有__proto__属性,这个属性对应该对象的原型.

    var p = new Person('张三',20);

    1. var p={}; 初始化一个对象p。
    2. p._proto_=Person.prototype;,将对象p的 __proto__ 属性设置为 Person.prototype
    3. Person.call(p,”张三”,20);调用构造函数Person来初始化p。关于call/apply使用

    总结:

    1. 所有的对象都有__proto__属性,该属性对应该对象的原型.
    2. 所有的函数对象都有prototype属性,该属性的值会被赋值给该函数创建的对象的_proto_属性.
    3. 所有的原型对象都有constructor属性,该属性对应创建所有指向该原型的实例的构造函数.
    4. 函数对象和原型对象通过prototype和constructor属性进行相互关联.


    (原文地址:https://zhuanlan.zhihu.com/p/23026595)

    <什么是原型>

    JavaScript 中,万物皆对象!但对象也是有区别的。分为普通对象和函数对象,Object ,Function 是JS自带的函数对象。

    每个对象都有原型(null和undefined除外),你可以把它理解为对象的默认属性和方法。

     Object:Object是一个函数对象,Object的原型就是一个Object对象,它里面存在着一些对象的方法和属性,例如最常见的toString方法。

    新建对象:用new Object或者{}建的对象是普通对象,它没有prototype属性,只有__proto__属性,它指向Object.prototype。

    Array:Array也是一个函数对象,它的原型就是Array.prototype,它里面存在着一些数组的方法和属性,例如常见的push,pop等方法。

    Function:Function也是一个函数对象,但它有点特殊,它的原型就是一个function空函数。

    自定义函数:它的原型就是你给它指定的那个东西。如果你不指定,那它的原型就是一个Object.prototype。

    <什么是原型链>

    在JavaScript 中,每个对象都有一个指向它的原型(prototype)对象的内部链接。这个原型对象又有自己的原型,直到某个对象的原型为 null 为止(也就是不再有原型指向),组成这条链的最后一环。这种一级一级的链结构就称为原型链(prototype chain)

    JavaScript 对象是动态的属性“包”(指其自己的属性)。JavaScript 对象有一个指向一个原型对象的链。

    当试图访问一个对象的属性时,它不仅仅在该对象上搜寻,还会搜寻该对象的原型,以及该对象的原型的原型,依此层层向上搜索,直到找到一个名字匹配的属性或到达原型链的末尾。

     当你用new Object或者直接定义一个对象时,它的原型链就是:

    o ==Object.prototype ==null;o._proto_==Object.prototype
    访问o上没有的属性或方法时,JS会往Object.prototype上寻找该属性和方法。
    如果有则直接返回,如果没有,方法则报错,这个方法未定义,属性则返回undefined

    o.__proto_指向原型对象,原型对象被赋值给创建的对象_proto_属性中.o对象没有prototype
     

     Person所有对象都有公共属性-Person.prototype = {age:24};

    Person是构造函数,tsrot函数对象(构造对象)。用构造函数(构造函数我们一般首字母大写)建立一个对象时,它的原型链就是 

     tsrot ==Person.prototype ==Object.prototype ==null

     tsrot.__proto__=Person.prototype;

    Person.prototype.__proto__=Object.prototype;

     

    Parent和child都是构造函数,

     

    fun是一个函数对象,它是由Function构造函数new的

    <prototype与__proto__>

    在Javascript中,每个函数都有一个原型属性prototype指向自身的原型,而由这个函数创建的对象也有一个__proto__属性指向这个原型,

    而函数的原型是一个对象(函数点prototype也是一个普通对象,Function.prototype除外,它是函数对象,但它很特殊,他没有prototype属性),

    所以这个对象也会有一个__proto__指向自己的原型,这样逐层深入直到Object对象的原型,这样就形成了原型链。

    普通对象没有prototype,但有__proto__属性。

     


    (原文地址https://www.cnblogs.com/tg666/p/12059205.html)

    Person 就是一个构造函数,使用 new 创建了一个实例对象 person

     

    prototype

      每个函数都有一个 prototype 属性

     

    proto

      每一个 javaScript 对象(null除外)都具有的一个属性叫 proto ,这个属性会指向该对象的原型

     

    constructor

      每一个原型都有一个 constructor 属性指向关联的构造函数,实例原型指向构造函数

     

     

     实例与原型

     

     原型与原型

    Person.prototype也是一个对象,具有_proto_属性指向Object的原型

     

     原型链


  • 相关阅读:
    最小覆盖点集模板
    NSCache使用常见错误
    stl变易算法(一)
    web.xml(8)_jsp-config
    大话设计模式—中介者模式
    HTML5开发移动web应用——SAP UI5篇(9)
    BZOJ 1588 HNOI2002 营业额统计 裸Treap
    php实现Bloom Filter
    华为上机之四
    【转】我的电脑最近忽然开不了机,启动修复也无法修复,win7系统。开机的时候如果不点启动修复直接正常启动
  • 原文地址:https://www.cnblogs.com/sun-null/p/13795424.html
Copyright © 2020-2023  润新知