闭包和继承

什么是闭包

闭包就是定义在一个函数内部的函数(函数嵌套函数),闭包就是将函数内部和函数外部连接起来的一座桥梁。

闭包的形成与变量的作用域以及变量的生存周期密切相关,变量的作用域,就是指变量的有效范围。生存周期对于全局变量是永久的,除非我们主动销毁这个全局变量。(垃圾回收机制)
而对于在函数内用 var 关键字声明的局部变量来说,当退出函数时,它们都会随着函数调用的结束而被销毁。

闭包特点:
–在一个函数内部定义另外一个函数,并且返回内部函数。
–内部函数可以读取外部函数定义的局部变量(利用函数内部的函数间接将函数内部的变量返回)
–让局部变量始终保存在内存中。也就是说,闭包可以使得它诞生环境一直存在。

(function() {
            var a = 100; //局部
            function fnA() {
                alert(a);
            }
            fnA();
        })();                  闭包的写法 - 开发的常见写法(不是最优)

闭包缺点:
–变量常驻内存,增加内存使用量–手动销毁,设为null
–使用不当会很容易造成内存泄漏–IE

闭包简单应用–tab切换

for (var i = 0; i < aBtn.length; i++) { 
            //i:0 - aBtn.length
            (function(i) {  
                //i:0 - aBtn.length
                aBtn[i].onmouseover = function() {
                    timer = setTimeout(() => {
                        for (var j = 0; j < aBtn.length; j++) {
                            aBtn[j].className = '';
                            aItem[j].style.display = 'none';
                        }
                        aBtn[i].className = 'active';
                        aItem[i].style.display = 'block';
                    }, 400);
                };

                aBtn[i].onmouseout = function() {
                    clearTimeout(timer);
                }
            })(i);
        }

原型链

每一个对象都有一个__proto__,JS在创建对象的时候,都有一个叫做__proto__的内置属性,用于指向创建它的函数对象的原型prototype。
概念:实例对象与原型(prototype)的连接,依靠__proto__内置属性实现的。

1、每个对象都有一个__proto__属性,原型链上的对象正是依靠这个属性连结在一起.

2、作为一个对象,当你访问其中的一个属性或方法的时候,如果这个对象中没有这个方法或属性,那么Javascript引擎将会访问这个对象的_proto属性所指向上一个对象,并在那个对象中查找指定的方法或属性,如果不能找到,那就会继续通过那个对象的_proto__属性指向的对象进行向上查找,直到这个链表结束。(null)
—如下原型链简图:
在这里插入图片描述
—面向对象的三大特点:封装,继承,多态。

继承

子类继承父类,但不影响父类。
–函数是对象,函数有属性和方法(length,call()/apply()/bind())
–类,构造函数 this - > 实例对象

面对对象开发的两种方式

混合开发 构造函数继承+原型)–混合继承

在这里插入图片描述
方法继承1 - 浅拷贝
将prototype下面的方法一一赋值给子类。

for (var i in Person.prototype) {
            Student.prototype[i] = Person.prototype[i]
        }

        Object.assign(Student.prototype, Person.prototype);

其中Object.assign()为es6新增.

方法继承2 - 原型继承:
将父类的实例给子类的原型。
Student.prototype = new Person(); //不但继承了Person.prototype的方法,同时修改了子类的构造函数体。
Student.prototype.constructor = Student; //重新设置子类的构造函数体。

ES6class开发

extends关键字:
Class 可以通过extends关键字实现继承,这比 ES5 的通过修改原型链实现继承,要清晰和方便很多。

super关键字:
子类必须在constructor方法中调用super方法,否则新建实例时会报错。这是因为子类自己的this对象,必须先通过父类的构造函数完成塑造,得到与父类同样的实例属性和方法,然后再对其进行加工,加上子类自己的实例属性和方法。如果不调用super方法,子类就得不到this对象。

super关键字既可以当作函数使用,也可以当作对象使用。
第一种情况,super作为函数调用时,代表父类的构造函数。
第二种情况,super作为对象时,在普通方法中,指向父类的原型对象;

–接上例:

class Student extends Person {
            constructor(name, age, sex, pro) {
                super(name, age, sex); //要得到与父类同样的实例属性和方法,必须先调用super方法,子类才能得到this对象,这里的super当函数用
                this.pro = pro;
            }

            showinfo() {
                return super.showinfo() + ',我的专业是' + this.pro; //super当对象使用
            }
        }

Prototype模式的其他验证方法

1.hasOwnProperty() : 看是不是对象自身下面的属性, 只在属性存在于实例中时才返回 true。
2.toString() :系统对象下面都是自带的 , 系统对象都有toString(),自己写的对象都是通过原型链找Object下面的,可以把对象转成字符串,可以做进制转换或者类型的判断(object.prototype.toString.call())。
3.constructor:实例对象的构造函数 (实例对象.constructor)
4.instanceof:判断一个对象是否是一个构造函数(类)的实例。

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

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值