网站制作方案和主要内容/优化快速排序
目录
- 一、前言
- 二、ES6与ES5继承机制区别
- 三、super作为函数
- 1、构造函数this
- 1)、首先要明确this指向
- ①、普通函数
- ②、箭头函数
- ③、注意事项
- 2)、其次要明确new操作符做了哪些事情
- 2、super()的用法及注意点
- 1)、用法
- 2)、注意点
- 四、super作为对象
- 1、super在子类普通方法中作为对象
- 2、super在子类静态方法中作为对象
- 五、总结
一、前言
类的继承可以通过extends实现,让子类继承父类的属性和方法,而在子类内部(构造函数constructor)必须调用super()实现继承(super()代表父类构造函数,调用之后生成一个继承父类的this对象)
二、ES6与ES5继承机制区别
- ES5的继承机制,是先创造一个独立的子类的实例对象,然后再将父类的方法添加到这个对象上面,即“实例在前,继承在后”
- ES6的继承机制,则是先将父类的属性和方法,加到一个空对象上面,然后再将该对象作为子类的实例,即“继承在先,实例在后”
- 所以ES6的继承必须先调用super(),这样会生成一个继承父类的this对象,没有这一步就无法继承父类。这意味着新建子类实例时,父类的构造函数必定会先运行一次
- super既可以作为函数使用,也可以作为对象使用,两种方法有很大的不同
三、super作为函数
super()作为函数调用时(子内constructor内部必须调用),代表父类的构造函数,调用之后生成的是子类的实例,即super()内部this指向的是子类的实例(由构造函数this指向可得出,构造函数内部this指向的是生成的实例,而super()调用之后生成的是子类实例)
1、构造函数this
1)、首先要明确this指向
①、普通函数
内部的this指向函数运行时所在的对象,也即指向函数的直接调用者
- 如果一个函数在全局环境运行,this就指向顶层对象(浏览器中为window对象)
- 如果一个函数作为某个对象的方法运行,this就指向那个对象
- 如果一个函数作为构造函数,this指向它的实例对象
②、箭头函数
没有自己的this对象,内部的this就是定义时上层作用域中的this
③、注意事项
构造函数只能是普通函数,箭头函数不能作为构造函数(没有prototype),不可以对箭头函数使用new命令,否则会抛出一个错误
2)、其次要明确new操作符做了哪些事情
- 创建一个空对象instance({})
- 将instance的[[prototype]]属性指向构造函数fn的原型(即instance.[[prototype]] = fn.prototype),也即instance的_ proto_要指向构造函数的原型prototype
- 执行构造函数,使用 call/apply 改变 this 的指向 => 让this指向创建出来的实例instance
- 若函数返回值的是对象类型则作为new方法的返回值返回,否则返回刚才创建的全新对象
function isObject (target) {return (typeof target === 'object' || typeof target === 'function') && target !== null
}
function myNew (fn, ...args) {// 使用Object.create(Y),就说明实例的__proto__指向了Y,即实例的原型对象是Y// Object.create():创建一个新对象,使用现有的对象来提供新创建的对象的__proto__// 并且执行[[Prototype]]链接; 通过`new`创建的每个对象将最终被`[[Prototype]]`链接到这个函数的`prototype`对象上。const instance = Object.create(fn.prototype)// 改变this指向let res = fn.apply(instance, args)// 若res是个对象就直接返回,否则返回创建的对象// return res instanceof Object ? res : instancereturn this.isObject(res) ? res : instance
}
如果不用new操作符直接调用,那么构造函数就相当于普通函数了,执行对象就 是window(严格模式下为undefined),即this指向了window(严格模式下为undefined)
由此可以看出,构造函数内部this指向实例对象
2、super()的用法及注意点
1)、用法
下面代码中,B是A的子类,B继承A,super虽然代表了父类A的构造函数,但是返回的是子类B的实例,即super内部的this指的是B的实例
B里边的super()在这里相当于A.prototype.constructor.call(this)
class A {constructor() {// `new.target`指向当前正在执行的函数console.log(new.target.name);}
}
class B extends A {constructor() {super();}
}
new A() // A
// 在`super()`执行时,它指向的是子类`B`的构造函数,而不是父类`A`的构造函数
// 即`super()`内部的`this`指向的是`B`的实例
new B() // B
new.target指向被new调用的构造函数:在普通的函数调用中(函数调用),new.target的值undefined;在类的构造方法中,new.target指向直接被new执行的构造函数
2)、注意点
- 子类的构造函数constructor内必须执行一次super函数
- 这是因为子类自己的this对象,必须先通过父类的构造函数完成塑造,得到与父类同样的实例属性和方法,然后再对其进行加工,添加子类自己的实例属性和方法。如果不调用super()方法,子类就得不到自己的this对象
- 新建子类实例时,父类的构造函数必定会先运行一次
- 在子类的构造函数中,只有调用super()之后,才可以使用this关键字,否则会报错
- super()调用之后才能让子类实例继承父类,然后才能在该基础上对子类实例进行属于它的特有操作
- 不管有没有显示定义,任何一个子类都有constructor()方法,而且里边默认会调用super()
- 作为构造函数时,super()只能用于在子类的构造函数之中,用在其他地方就会报错
- 使用super()的时候,必须显示指定是作为函数,还是作为对象使用,否则会报错
- 由于对象总是继承其他对象的,所以可以在任意一个对象中,使用super关键字
四、super作为对象
super作为对象时,在子类普通方法中,指向父类的原型对象;在子类静态方法中,指向父类
1、super在子类普通方法中作为对象
当super作为对象在子类普通方法(非静态方法)中使用时,由于super指向父类的原型对象,所以定义在父类原型对象上的属性和方法都可以被访问到,而定义在父类实例上(父类构造函数this.xxx)的方法或属性无法被访问到
在子类普通方法中通过super调用父类的方法时,方法内部的this指向当前的子类实例,相当于执行的是super.fn.call(this)
下面的代码中,父类A有定义在原型对象的属性b和方法p(),还有定义在实例对象的属性a;可以看到的是,定义在原型对象的b和p都能被super.访问到,而定义在实例对象的a无法被访问到
class A {constructor() {this.a = 123 // 定义在A的实例上的属性a}// 定义在A.prototype上的方法p() {return 2;}
}A.prototype.b = 123 // 定义在A原型对象的属性bclass B extends A {constructor() {super();console.log(super.p()); // 2 => 相当于console.log(A.prototype.p())}getData() {console.log(super.a) // a定义在父类的实例对象上,所以为undefinedconsole.log(super.b) // b定义在父类的原型对象上,所以为123}
}let b = new B();b.getData()
在子类普通方法中通过super调用父类的方法时,方法内部的this指向当前的子类实例,相对于执行的是super.fn.call(this)
class A {constructor() {this.x = 1; // 父类实例的x是1}print() {console.log(this.x);}
}class B extends A {constructor() {super();this.x = 2; // 子类实例的x是2}m() {// 实际上执行的是`super.print.call(this)`super.print(); // 调用父类的方法,但是方法内部this是子类实例,所以输出2}
}let b = new B();
b.m() // 2
由于this指向子类实例,所以如果通过super对某个属性赋值,这时super就是this,赋值的属性会变成子类实例的属性
class A {constructor() {this.x = 1;}
}class B extends A {constructor() {super();this.x = 2;super.x = 3;console.log(super.x); // undefinedconsole.log(this.x); // 3}
}let b = new B();
上面代码中,super.x赋值为3,这时等同于对this.x赋值为3。而当读取super.x的时候,读的是A.prototype.x,所以返回undefined
2、super在子类静态方法中作为对象
当super作为对象在子类静态方法中使用时,这时super将指向父类,而不是父类的原型对象。在子类的静态方法中通过super调用父类的方法时,方法内部的this指向当前的子类,而不是子类的实例
class Parent {static myMethod(msg) {console.log('static', msg);}myMethod(msg) {console.log('instance', msg);}
}class Child extends Parent {static myMethod(msg) {// super作为对象在子类静态方法中使用,super指向的是父类// 也即要调用父类的myMethod方法,那就是父类的静态方法Parent.myMethod// 而属于一个类的方法,就是静态方法,也就是由static关键字定义的方法super.myMethod(msg); // 调用的是Parent.myMethod()}myMethod(msg) {// super作为对象在子类普通方法中使用,super指向的是父类的原型对象// 此时的super.myMethod()也即Parent.prototype.myMethod()// 由class语法糖和原来构造函数创建类的写法相对比可知super.myMethod(msg);}
}Child.myMethod(1); // static 1var child = new Child();
child.myMethod(2); // instance 2
五、总结
通过本文的介绍,我们了解了在ES6中使用extends关键字实现继承,并且学习了super()在子类中的用法和作用以及注意点。super()的正确使用可以让我们更加方便地在子类中调用父类的构造函数和方法,从而更加灵活地使用面向对象编程。希望本文能够帮助各个小伙伴更好地理解ES6中Class继承的super()关键字。
相关文章:

【ES6】Class继承-super关键字
目录 一、前言二、ES6与ES5继承机制区别三、super作为函数1、构造函数this1)、首先要明确this指向①、普通函数②、箭头函数③、注意事项 2)、其次要明确new操作符做了哪些事情 2、super()的用法及注意点1)、用法2)、注意点 四、s…...

做亚马逊测评不知道怎么找客户?这才是亚马逊测评的正确打开方式!
如今的跨境电商内卷严重,花费大量资金做广告推广的效果却微乎其微,这也是亚马逊测评迅速崛起的最根本原因。做亚马逊测评是近年来兴起的一种方式,许多卖家都需要大量的测评来提高自己的产品排名和信誉度。很多兄弟最近来问龙哥亚马逊测评怎么…...

传感器基础:传感器使用与编程使用(三)
目录 常用传感器讲解九--雨滴传感器具体讲解电路连接代码实现 常用传感器讲解十--光传感器根据亮度安排灯具体讲解电路连接代码实现 常用传感器讲解七--light cup(KY-008)具体讲解电路连接代码实现 常用传感器讲解十二--倾斜开关传感器(KY-02…...

深入浅出:分布式、CAP 和 BASE 理论(荣耀典藏版)
大家好,我是月夜枫,一个漂泊江湖多年的 985 非科班程序员,曾混迹于国企、互联网大厂和创业公司的后台开发攻城狮。 在计算机科学领域,分布式系统是一门极具挑战性的研究方向,也是互联网应用中必不可少的优化实践&…...
vue3+elementPlus:el-drawer新增修改弹窗复用
在el-drawer的属性里设置:title属性,和重置函数 //html<!-- 弹窗 --><el-drawerv-model"drawer":title"title":size"505":direction"direction":before-close"handleClose"><el-formlabel-posit…...

使用Docker快速安装grafana
Docker 提供了一个轻量级、易于部署的容器化解决方案,让您能够方便地在不同环境中运行应用程序。以下是在 Docker 中安装 Grafana 的基本步骤: 文章目录 使用Docker快速安装grafana如何使用Grafana步骤 1:连接数据源步骤 2:创建仪…...

excel 函数技巧
1:模糊查询 LOOKUP(1,0/FIND(F1062,Sheet1!C$2:Sheet1!C$9135),Sheet1!B$2:Sheet1!B$9135) 函数含义:寻找F列1062行和sheet1中的C2行到C9135行进行模糊查询,返回该行对应的B2行到B9135行的结果。未查到返回结果0 函数公式: LO…...

Ubuntu安装WordPress并使用Nginx作为Web服务器
在Ubuntu上安装和配置WordPress并使用Nginx作为Web服务器,以下是一个简单的操作流程: 步骤 1: 安装Nginx sudo apt update sudo apt install nginx 启动Nginx并设置开机自启: sudo systemctl start nginx sudo systemctl enable nginx …...

[Linux]Ubuntu noVNC使用
又到了逛大型程序员交友 网站的时间了,今天你准备好了吗。 今天要推荐的一个有趣的项目是noVNC setup好以后是这个样子的,可以在浏览器登陆vnc,不需要再安装一个vnc client. setup的过程比较简单,分为以下几步: 1. v…...

CSRF和SSRF原理、区别、防御方法
CSRF(Cross-Site Request Forgery)原理:CSRF是一种由攻击者构造形成,由服务端发起请求的一个安全漏洞。它是一种利用用户在已登录的网站中提交非法请求的行为,攻击者通过伪造用户提交的请求,将恶意请求发送…...

如何使用JMeter测试https请求
HTTP与HTTPS略有不同,所以第一次使用JMeter测试https请求时遇到了问题,百度一番后找到解决方法:加载证书。 下面内容主要记录这次操作,便于后续参考: 操作浏览器:谷歌 (1)下载被测…...

el-table 纵向垂直表头
<template><div class"element-main"><div> Element-ui 官方提供 table Demo</div><el-tableborderstyle"width: 100%":data"tableData"><el-table-column prop"courseName" label"课程信息&qu…...

python/pytorch读取数据集
MNIST数据集 MNIST数据集包含了6万张手写数字([1,28,28]尺寸),以特殊格式存储。本文首先将MNIST数据集另存为png格式,然后再读取png格式图片,开展后续训练 另存为png格式 import torch from torch.utils.data impor…...

IT安全:实时网络安全监控
了解庞大而复杂的网络环境并非易事,它需要持续观察、深入分析,并对任何违规行为做出快速反应。这就是为什么实时网络安全监控工具是任何组织 IT 安全战略的一个重要方面。 网络攻击和合规性法规是 IT 安全的两个主要驱动因素。同时,数据泄露…...

SQL server使用profiler工具跟踪语句
1.打开SQL server工具,在工具点击SQL server Profiler : 2.流程:暂停——清空———点击接口——启用: 3.找到对应的sql语句,复制到查询界面,开始查询数据:...

python实现一维傅里叶变换——冈萨雷斯数字图像处理
原理 傅立叶变换,表示能将满足一定条件的某个函数表示成三角函数(正弦和/或余弦函数)或者它们的积分的线性组合。在不同的研究领域,傅立叶变换具有多种不同的变体形式,如连续傅立叶变换和离散傅立叶变换。最初傅立叶分…...

表单(HTML)
<!DOCTYPE html> <html><head><meta charset"utf-8"><title>个人信息</title></head><body><h1>个人信息</h1><form><fieldset><legend>基本信息</legend><label for"…...

spripng 三级缓存,三级缓存的作用是什么? Spring 中哪些情况下,不能解决循环依赖问题有哪些
文章目录 前面有提到三级缓存,三级缓存的作用是什么?Spring 中哪些情况下,不能解决循环依赖问题: 前面有提到三级缓存,三级缓存的作用是什么? 上一篇:https://blog.csdn.net/weixin_44797327/a…...

elasticsearch系列六:索引重建
概述 我们再起初创建索引的时候由于数据量、业务增长量都并不大,常常不需要搞那么多分片或者说某些字段的类型随着业务的变化,已经不太满足未来需求了,再或者由于集群上面索引分布不均匀导致节点直接容量差异较大等等这些情况,此时…...

GitOps实践指南:GitOps能为我们带来什么?
Git,作为开发过程中的核心工具,提供了强大的版本控制功能。即便在写代码的时候稍微手抖一下,我们也能通过 Git 的差异对比(diff)轻松追踪到庞大工程中的问题,确保代码的准确与可靠。这种无与伦比的自省能力…...

D3485国产芯片+5V工作电压, 内置失效保护电路采用SOP8封装
D3485是一款5V供电、半双工的RS-485收发器,芯片内部包含一路驱动器和路接收器。D3485使用限摆率驱动器,能显著减小EMI和由于不恰当的终端匹配电缆所引起的反射,并实现高达10Mbps的无差错数据传输。D3485内置失效保护电路,保证接收…...

devops使用
官方文档 使用 Git 进行代码 - Azure DevOps | Microsoft Learn...

AI训练师常用的ChatGPT通用提示词模板
AI模型选择:如何选择合适的AI模型? 数据集准备:如何准备用于训练的数据集? 数据预处理:如何对待训练数据进行预处理? 特征工程:如何进行特征选择和特征工程? 超参数调整…...

Java加密算法工具类(AES、DES、MD5、RSA)
整理了有关加密算法工具类,结合了几个博客以及自己改良后可直接使用,主要介绍以下四种加密方式:AES、DES、MD5、RSA,详细介绍都在注释里面有讲。 一、AES import com.alibaba.fastjson.JSONObject; import java.nio.charset.Sta…...

探索Go语言的魅力:一门简洁高效的编程语言
介绍Go语言: Go,也被称为Golang,是由Google开发的一门开源编程语言。它结合了现代编程语言的优点,拥有高效的并发支持和简洁的语法,使其成为构建可伸缩、高性能应用的理想选择。 Go语言的特性: 并发编程…...

【用unity实现100个游戏之19】制作一个3D传送门游戏,实现类似鬼打墙,迷宫,镜子,任意门效果
最终效果 文章目录 最终效果素材第一人称人物移动开门效果显示原理渲染相机跟着我们视角移动门的摄像机跟着我们旋转近裁剪面设置传送配置代码实现传送效果结束完结素材 https://assetstore.unity.com/packages/3d/props/interior/door-free-pack-aferar-148411...

DRF(Django Rest Framework)框架基于restAPI协议规范的知识点总结
Django Rest Framework学习 一、初识DRF组件 1.1 FBV和CBV FBV:function based view from django.shortcuts import render, HttpResponse # 这种是基于FBV模式 函数模式实现Views函数 def login(request):if request.method GET:return HttpResponse("Get…...

Linux磁盘与文件系统管理
目录 在linux系统中使用硬盘 磁盘的数据结构 磁盘接口类型 字母含义 MBR磁盘分区 分区类型 分区的缺点 文件系统的 文件系统有什么作用 文件系统的修复 检测并确认新磁盘 参看磁盘信息 查看磁盘信息 添加磁盘 查看添加磁盘情况:sda系统磁盘ÿ…...

数字魔法AI绘画的艺术奇迹-用Stable Diffusion挑战无限可能【文末送书-12】
文章目录 前言一. 技术原理1.1 发展历程 二.对艺术领域的影响三. 挑战与机遇四.AI魔法绘画:用Stable Diffusion挑战无限可能【文末送书-12】4.1 粉丝福利:文末推荐与福利免费包邮送书! 前言 随着人工智能技术的迅猛发展,AI在各个…...

【docker实战】02 用docker安装mysql
本示例采用bitnami的镜像进行安装MySQL 一、镜像搜索 先搜索一下mysql有哪些镜像 [rootlocalhost ~]# docker search mysql NAME DESCRIPTION STARS OFFICIAL AUTOMATED mysql …...