03-原型继承

学习目标

一、复习
  • 1、由于实例对象的原型指向的就是构造函数的原型可以省去__proto__

  • 实例对象中的__proto__指向的就是该实例对象中的构造函数中的prototype

  • 2、为什么使用原型?

  • 本身在构造函数中定义的属性和方法,当实例化对象的时候,实例对象中的属性和方法都是在自己的空间中存在的,如果是多个对象。这些属性和方法都会在单独的空间中存在,浪费内存空间,所以,为了数据共享,把想要节省空间的属性或者方法写在原型对象中,达到了数据共享,实现了节省内存空间

  • 3、如果构造函数中的:属性或者方法实现的效果都是一样的,那么可以写到原型对象当中

  • 4、当内置对象不满足需求可以通过原型为内置对象添加属性或方法,方便开发

  • 5、高内聚、低耦合

  • 6、面向对象的思想来做: 分析对象,抽象出对象的特征和行为,定义构造函数,属性可以不共享部分方法需要共享,方法加到prototype中定义(在原型中定义方法,数据共享,节省内存空间)

  • 7、window.变量=值;把这个局部变量的值暴露给window,成为了全局变量

  • 8、对象.bind(参数);---->改变this的指向

面向对象编程思想:

根据需求,分析对象,找到对象有什么特征和行为,通过代码的方式来实现需求,要想实现这个需求,就要创建对象,要想创建对象,就应该先有构造函数,然后通过构造函数来创建对象,通过对象调用属性和方法来实现相应的功能及需求,即可

一、实例对象和构造函数之间有没有直接关系?
  • 没有
  • 而真正的实例对象和原型对象有关系,实例对象和原型对象之间的关系叫原型链,这种关系通过__proto__
二、原型链
  • 原型链:是一种关系,实例对象和原型对象之间的关系,关系是通过原型(__proto__)来联系的
  • 如果想要使用一些属性和方法,并且属性的值在每个对象中都是一样的,方法在每个对象中的操作都是一样,那么,为了共享数据,节省内存空间,是可以把每个属性和方法通过原型的方式赋值

[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-uKBQ4NI4-1580717960781)(media\原型链.jpg)]

三、原型的指向是否可以改变

[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-BklaSiPi-1580717960783)(media\原型的指向是可以改变的.jpg)]

  • 原型的指向是可以发生改变的

  • 实例对象的原型__proto__指向的是该对象所在的构造函数的原型对象

  • 构造函数的原型对象(prototype)指向如果改变了,实例对象的原型(__proto__)指向也会发生改变

  • 原型的指向是可以改变的

  • 实例对象和原型之间的关系是通过__proto__原型来联系的,这个关系就是原型链

四、原型最终指向了哪里?
  • 实例对象中有__proto__原型

  • 构造函数中有prototype原型

  • prototype是对象

  • 所以,prototype这个对象中也有__proto__,那么指向了哪里

  • 实例对象中的__proto__指向的是构造函数的prototype

  • 所以,prototype这个对象中的__proto__指向的应该是某个构造函数的原型prototype

  • Person的prototype中的__proto__的指向

  • console.log(Person.prototype.__proto__);

  • per实例对象的__proto__——>Person.prototype的__proto__——>Object.prototype的__proto__是null

    [外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-XmccTvgM-1580717960784)(media\原型链最终的指向是Object的prototype的_proto__是null.jpg)]

五、原型指向改变如何添加方法和访问

改变了原型对象的指向:构造函数.prototype = new Person(10);

  • 如果原型指向改变了,那么就应该在原型改变之后添加原型方法
六、实例对象对象的属性和原型对象属性重名问题
  • 实例对象访问这个属性,应该先从实例对象中去找,找到了就直接使用,找不到就去指向的原型对象中去找,找到了就使用,找不到呢?——>undefined

  • 通过实例对象能否改变原型对象中的属性值?不能
    就想改变原型不过对象中属性的值,怎么办?直接通过原型对象.属性=值;可以改变

  • 原型链:实例对象和原型对象之间的关系,通过__proto__

七、div对象原型链最终的指向
 var divObj = document.getElementById("dv");
 console.dir(divObj);//查看对象结构
divObj.__proto__——>HTMLDivElement.prototype的__proto__——>Node.prototype的__proto__——>EventTarget.prototype的__proto__——>Object.prototype没有__proto__,所以Object.prototype中的__proto__是null
八、原型继承
  • 继承的目的:解决代码重复,造成了代码的冗余

  • 改变构造函数的原型的指向即可

  • 语法:

    构造函数.prototype = new 对象();

    因为任何实例对象中都会__proto__原型对象,指向的是该实例对象中的构造函数中的prototype

九、借用构造函数实现继承
  • 为了数据共享,改变原型指向,做带了继承——>通过改变原型指向实现的继承

  • 缺陷:因为改变原型指向的同时实现继承,直接初始化了属性,继承过来的属性的值都是一样的了,所以,这就是问题,只能重新调用对象的属性进行重新赋值

  • 解决方案:继承的时候,不用改变原型的指向,直接调用父级的构造函数的方式来为属性赋值就可以了——>借用构造函数:把要继承的父级的构造函数拿过来,使用一下就可以了

  • 借用构造函数:构造函数名字.call(当前对象,属性,属性,属性…)

  • 解决了属性继承,并且值不重复的问题

  • 缺陷:父级类别的方法不能继承

十、拷贝继承(for in)
  • 浅拷贝:被没有把原型对象中__proto__指向的原型对象继承过来
  • 拷贝继承:把一个对象中的属性或者方法直接复制到另一个对象中
  • 遍历prototype对象的属性或者方法
十一、总结继承
  • 继承:类与类之间的关系,面向对象的语言的继承是为了多态服务的
  • js不是一门面向对象语言,但是可以模拟面向对象,模拟继承,为了节省内存空间
  • 继承:
  • 原型作用之一:数据共享 目的是:为了节省内存空间
  • 原型作用之二:继承 目的是:为了节省内存空间
  • 原型继承:改变原型指向 缺陷:属性值直接被初始化
  • 借用构造函数继承:主要解决属性的问题 缺陷:父类中的方法不能被继承
  • 组合继承:原型继承(不传值)+借用构造函数继承
    既能解决属性问题,又能解决方法的问题
  • 拷贝继承:就是把对象中需要共享的属性或者方法,直接遍历的方式复制到另一个对象中
十二、逆推继承看原型

[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-OHQnhLF3-1580717960785)(media\逆推继承看原型.jpg)]

十三、函数中this指向的问题
调用方式非严格模式备注
普通函数调用window严格模式下是 undefined
构造函数调用实例对象原型中方法中this也是实力对象
对象方法调用该方法所属的对象紧挨着的对象
事件绑定方法绑定事件对象
定时器函数window
十四、严格模式

开启严格模式:"use strict";

  function f1() {
        console.log(this);
    }
    f1();//开启严格模式输出的是undefined,除非加window
十五、函数的角色

函数的声明:

 function f1(){
   console.log("我是函数");
}
f1();

函数表达式:

var ff= function () {
    console.log("我也是一个函数哟");
}
ff();

函数声明如果在if-else的语句中,在IE8浏览器中会出现问题问题:IE8中:会预解析,把函数提升,后面的函数把前面同名函数替换了以后宁愿用函数表达式,都不用函数声明

十六、函数也是对象
  • 函数是对象,对象不一定是函数
  • 对象中__proto__原型,是对象
  • 函数中有prototype原型,是对象
  • 如果一个东西里面有prototype,又有__proto__,说明是函数,也是对象
  • 所有的函数实际上都是Function的构造函数创建出来的实例对象
十七、数组中forEacs方法

回调函数:函数作为参数使用
Array.forEach(function(ele){
ele就是数组中每个元素
});

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值