1.面向对象初识
(1) 定义:js中有两种编程思想
① 面向过程:按照步骤,一步一步将代码编写完,整个编程是一个过程。
② 面向对象:遇到问题 使用对象来解决,如果没有对象,就创建(封装)对象 来解决问题
(2) 面向对象的三大基本特征
① 封装:将一些特征和功能 封装为一个对象, 目的是为了提高这些功能和特征的安全性。 同时有助于实现 高内聚低耦合 一处出错,其他对象不受影响
② 继承:一个类可以通过继承的方式,得到其他类中的属性和方法。
③ 多态:同一操作 在 不同情况下 会得到 不同的结果
1) 例如: + 如果两个操作数中没有字符串 就按照数字运算 如果有字符串,就是字符串的拼接
④ 在ES5的范畴内 不存在真正的面向对象
(3) 对象中的重要概念
① 属性:静态的,用来描述对象的特征
② 方法:动态的,用来描述对象的行为
2.对象的创建
(1) 字面量创建
①
② 优点:直观,易写
③ 缺点:不利于批量创建对象
(2) 实例化创建对象
①
② 优点:可以使对象的类型更明确
③ 缺点:并没有解决批量创建对象的问题。
(3) 工厂模式创建对象(是js八种设置模式之一)
①
② 优点:可以批量创建对象
③ 缺点:工厂模式的函数中 this指向window 而不是实际创建出的对象。 因此在函数中不能通过this 来操作创建的对象
(4) 构造函数创建对象
① Date String Array Object 这些都是构造函数
② 写法:
1)
2) 优点:可以很方便的批量创建对象,并且this指向创建出来的对象
3) 缺点:当构造函数创建的对象中 有重复属性的时候 就产生了 内存的浪费
4) 构造函数执行步骤:
(5) 原型创建
① 原型:每一个对象都有原型 对象.__proto__===对象的原型
1) 原型也是对象
2) 原型也可以通过 构造函数来获取 构造函数.prototype === 原型
3) 原型.constructor === 原型对应的构造函数
4)
5) 原型的作用:原型对象可以将自己的属性 全部 继承给 子对象
- 继承:原型中的属性 子对象都可以使用 但不拥有。
6) 注意:任何子对象都可以使用原型的属性
② 原型创建对象
1) 将属性存放在原型中 继承给 所有子对象
2)
3) 优点:可以最大限度节省内存
4) 缺点:子对象没有属性,原型中的属性不能随意修改
(6) 混合式创建
① 思路:将容易改变的属性写入构造函数中 给对象绑定, 将不易改变的属性 写入原型中给对象继承, 从而实现在可以灵活修改属性值的基础上 最大限度节省内存的效果
② 推荐使用
- 对象的实例
(1) This指向
① 构造函数的this--->他自己创建出来的对象
② 方法函数的this--->调用它的对象
③ 事件处理函数的this--->添加事件的元素对象
3.面向对象的继承
(1) 原型链继承
① 原型链:
每一个对象 都有原型,原型也是对象,也有自己的原型。因此我们说------从子对象开始,到Object.prototype结束,这之间存在着一个由__proto__属性连接起来的链式结构,我们称之为原型链
1) 原型链中任意一个原型中的属性 都会最终继承给 子对象
2) 原型链的属性查找原则:
一个对象访问属性,会先在自身中查找,如果有就使用,如果没有,就去原型中查找,有就用,没有就继续向上一级原型中查找,一直找到Object.prototype,如果有就用 如果还没有返回undefined
② 原型链继承
1)
2) 弊端:由于子对象的属性都是继承来的 因此不能随意改变,不灵活
3) 优点:可以继承到原型链中的属性
(2) 对象冒充继承
① Call,apply
1) Call:是函数的方法,作用是修改函数的this指向
- 用法:函数.call(要修改的this指向,原函数需要的参数1,参数2,参数3...)
- 注意:当函数调用了call方法之后,修改完this指向 会立即执行
2) Apply:也是函数的方法 作用和call完全一样
- 用法:函数.apply(要修改的this指向,[原函数需要的参数1,参数2...])
② 对象冒充继承
1)
2) 弊端:骗子构造函数的 子对象 无法继承到 原型链中的属性
3) 优点:可以随意修改子对象的属性值
(3) 混合式继承
① 使用原型链继承 继承原型链中的属性 使用对象冒充继承 继承到 构造函数中的属性(可以随意修改的)
②
③ 优点:可以直接得到太后构造函数中的所有属性,进而就可以随意修改属性的值,并且也可以得到原型链中的属性
④ 缺点:浪费了内存
(4) 寄生混合式继承
① 相对比混合式继承 唯一的优点是 节省了内存
②
备注:以上所举实例,只是为了更清楚理解,不具体指谁,纯属虚构。