浅谈ES6中的Class
转载地址:https://www.cnblogs.com/sghy/p/8005857.html
一、定义类(ES6的类,完全可以看做是构造函数的另一种写法)

- class Greet {
- constructor(x, y) {
- this.x = x;
- this.y = y;
- }
- sayHello() {
- console.log(this.x + " " + this.y)
- }
- }
- let a = new Greet("hello", "everybody");
- a.sayHello() //hello everybody

《注》:
- 以上定义的类如果用ES5的构造函数实现如下:

- function Greet(x, y) {
- this.x = x;
- this.y = y;
- this.sayHello = function () {
- console.log(this.x + " " + this.y)
- }
- }
- let a = new Greet("hello", "everybody");
- a.sayHello() //hello everybody

- 类的数据类型就是函数,类本身就指向构造函数
- typeof Greet; //function
- Greet === Greet.prototype.constructor //true
- 类的所有方法都定义在类的
prototype
属性上面

- class Greet {
- constructor() {...}
- sayHello() {...}
- sayHi(){...}
- }
- 等同于
- Greet
- Greet.prototype = {
- constructor() {},
- sayHello() {},
- sayHi() {},
- };

- constructor方法:
- 是类的默认方法,通过
new
命令生成对象实例时,自动调用该方法。一个类必须有constructor
方法,如果没有显式定义,一个空的constructor
方法会被默认添加。
- class Greet {
- }
- // 等同于
- class Greet {
- constructor() {}
- }
constructor
方法默认返回实例对象(即this
),完全可以指定返回另外一个对象。

- class Foo {
- constructor() {
- return Object.create(null);
- }
- }
- new Foo() instanceof Foo
- // false

类的实例对象:
- 实例的属性除非显式定义在其本身(即定义在
this
对象上),否则都是定义在原型上(即定义在class
上)。

- class Greet {
- constructor(x, y) {
- this.x = x;
- this.y = y;
- }
- sayHello() {
- console.log(this.x + " " + this.y)
- }
- }
- let a = new Greet("hello", "everybody");
- // x,y都是实例对象a自身的属性,因为定义在this上
- a.hasOwnProperty('x') // true
- a.hasOwnProperty('y') // true
- //sayHello是原型对象的属性,因为定义在Greet上
- a.hasOwnProperty('sayHello') // false
- a.__proto__.hasOwnProperty('sayHello') // true

- 类的所有实例共享一个原型对象
- let a = new Greet("hello", "everybody");
- let b = new Greet("hello", "everybody");
- a.__proto__ === b.__proto__ //true
Class表达式:

- const MyClass = class Me {
- getClassName() {
- return Me.name;
- }
- }; //类的名字是MyClass而不是Me,Me只在 Class 的内部代码可用,指代当前类。
- //如果类的内部没用到的话,可以省略Me
- const MyClass = class {
- ...
- };

不存在变量提升:必须先定义类,再使用
私有方法:
- 利用
Symbol
值的唯一性

- const bar = Symbol('bar');
- const snaf = Symbol('snaf');
- export default class myClass{
- // 公有方法
- foo(baz) {
- this[bar](baz);
- }
- // 私有方法
- [bar](baz) {
- return this[snaf] = baz;
- }
- // ...
- };

- 利用#标识:

- class Greet {
- constructor(x, y) {
- this.x = x;
- this.y = y;
- }
- #sayHello() {
- console.log(this.x + " " + this.y)
- }
- }

Class 的取值函数(getter)和存值函数(setter):在“类”的内部可以使用get
和set
关键字,对某个属性设置存值函数和取值函数,拦截该属性的存取行为。

- class MyClass {
- constructor() {
- // ...
- }
- get prop() {
- return 'getter';
- }
- set prop(value) {
- console.log('setter: '+value);
- }
- }
- let inst = new MyClass();
- inst.prop = 123;
- // setter: 123
- inst.prop
- // 'getter'

Class 的静态方法:加上static
关键字,表示该方法不会被实例继承,而是直接通过类来调用

- class Foo {
- static classMethod() {
- return 'hello';
- }
- }
- Foo.classMethod() // 'hello'
- var foo = new Foo();
- foo.classMethod()
- // TypeError: foo.classMethod is not a function

- 如果静态方法包含
this
关键字,这个this
指的是类,而不是实例 - 父类的静态方法,可以被子类继承
- 静态方法也是可以从
super
对象上调用的
Class 的静态属性和实例属性
- 静态属性指的是 Class 本身的属性,即
Class.propName
,而不是定义在实例对象(this
)上的属性,定义方法如下:

- class MyClass {
- static myStaticProp = 42;
- constructor() {
- console.log(MyClass.myStaticProp); // 42
- }
- }

- 类的实例属性可以用等式,写入类的定义之中

- class MyClass {
- myProp = 42;
- constructor() {
- console.log(this.myProp); // 42
- }
- }

new.target 属性:如果构造函数不是通过new
命令调用的,new.target
会返回undefined
用来确定构造函数是怎么调用的。

- function Person(name) {
- if (new.target !== undefined) {
- this.name = name;
- } else {
- throw new Error('必须使用 new 命令生成实例');
- }
- }

二、Class继承:通过extends
关键字实现继承
- class Point {
- }
- class ColorPoint extends Point {
- }
supper:
- 子类必须在
constructor
方法中调用super
方法(子类没有自己的this
对象,而是继承父类的this
对象,然后对其进行加工)

- class Point { /* ... */ }
- class ColorPoint extends Point {
- constructor() {
- }
- }
- let cp = new ColorPoint(); // ReferenceError

- 如果子类没有定义
constructor
方法,这个方法会被默认添加

- class ColorPoint extends Point {
- }
- // 等同于
- class ColorPoint extends Point {
- constructor(...args) {
- super(...args);
- }
- }

- 在子类的构造函数中,只有调用
super
之后,才可以使用this
关键字(子类实例的构建,是基于对父类实例加工,只有super
方法才能返回父类实例)

- class Point {
- constructor(x, y) {
- this.x = x;
- this.y = y;
- }
- }
- class ColorPoint extends Point {
- constructor(x, y, color) {
- this.color = color; // ReferenceError
- super(x, y);
- this.color = color; // 正确
- }
- }

super
作为函数调用时,代表父类的构造函数。ES6 要求,子类的构造函数必须执行一次super
函数。且只能用在子类的构造函数之中,用在其他地方就会报错

- class A {}
- class B extends A {
- constructor() {
- super();
- }
- } //
super
虽然代表了父类A
的构造函数,但是返回的是子类B
的实例

super
作为对象时,在普通方法中,指向父类的原型对象;在静态方法中,指向父类。
a)普通方法中:

- class A {
- p() {
- return 2;
- }
- }
- class B extends A {
- constructor() {
- super();
- console.log(super.p()); // 2
- }
- } //指向父类的原型对象
- let b = new B();

b) 静态方法中:

- class Parent {
- static myMethod(msg) {
- console.log('static', msg);
- }
- myMethod(msg) {
- console.log('instance', msg);
- }
- }
- class Child extends Parent {
- static myMethod(msg) {
- super.myMethod(msg);
- }
- myMethod(msg) {
- super.myMethod(msg);
- }
- }
- Child.myMethod(1); // static 1
- var child = new Child();
- child.myMethod(2); // instance 2

浅谈ES6中的Class的更多相关文章
- 浅谈ES6中super关键字
作用: super 关键字用于访问父对象上的函数. 语法: super([arguments]); // 访问父对象上的构造函数 super.functionOnParent([arguments]) ...
- 浅谈ES6中的Async函数
转载地址:https://www.cnblogs.com/sghy/p/7987640.html 定义:Async函数是一个异步操作函数,本质上,Async函数是Generator函数的语法糖.asy ...
- 浅谈ES6中的Proxy
Proxy是一个很有趣的对象,它能够修改某些操作的默认行为,等同于在语言层面做出修改,属于一种‘元编程’,即对编程语言进行编程. Proxy其实很好理解,就是在目标对象之前架设一层拦截,外界的访问都得 ...
- 浅谈ES6原生Promise
浅谈ES6原生Promise 转载 作者:samchowgo 链接:https://segmentfault.com/a/1190000006708151 ES6标准出炉之前,一个幽灵,回调的幽灵,游 ...
- 浅谈JS中 var let const 变量声明
浅谈JS中 var let const 变量声明 用var来声明变量会出现的问题: 1. 允许重复的变量声明:导致数据被覆盖 2. 变量提升:怪异的数据访问.闭包问题 3. 全局变量挂载到全局对象:全 ...
- 浅谈Java中的equals和==(转)
浅谈Java中的equals和== 在初学Java时,可能会经常碰到下面的代码: 1 String str1 = new String("hello"); 2 String str ...
- 浅谈Linux中的信号处理机制(二)
首先谢谢 @小尧弟 这位朋友对我昨天夜里写的一篇<浅谈Linux中的信号处理机制(一)>的指正,之前的题目我用的“浅析”一词,给人一种要剖析内核的感觉.本人自知功力不够,尚且不能对着Lin ...
- 浅谈Java中的对象和引用
浅谈Java中的对象和对象引用 在Java中,有一组名词经常一起出现,它们就是“对象和对象引用”,很多朋友在初学Java的时候可能经常会混淆这2个概念,觉得它们是一回事,事实上则不然.今天我们就来一起 ...
- 浅谈Java中的equals和==
浅谈Java中的equals和== 在初学Java时,可能会经常碰到下面的代码: String str1 = new String("hello"); String str2 = ...
随机推荐
- 自动化安装操作系统(Centos7+PXE+Cobbler+kickstart)
一.简介 PXE称作是一种引导方式而不是安装方式似乎更加准确,PXE(Pre-boot Execution Environment)是由Intel设计的协议,它可以使计算机通过网络启动,但是有一个前提 ...
- linux作业--第十周
1.在阿里云服务器搭建openv-p-n(有条件的同学再做) 2.通过编译.二进制安装MySQL5.7 编译安装MySQL5.7 安装相关包 yum -y install libaio numactl ...
- Linux网卡ifcfg-eth0配置详解
DEVICE="eth1" 网卡名称 NM_CONTROLLED="yes" n ...
- tp5怎么防sql注入 xss跨站脚本攻击
在 application/config.php 中有个配置选项 框架默认没有设置任何过滤规则,你可以是配置文件中设置全局的过滤规则 则会调用这些函数 自动过滤 // 默认全局过滤方法 用逗号分隔多个 ...
- EXSI6.7 中给虚拟机磁盘扩容
[admin@localhost ~]$ sudo fdisk -l Disk /dev/sda: 214.7 GB, 214748364800 bytes, 419430400 sectors Un ...
- django的request对象方法初识
1:request.post 拿到的是post请求发送过来的数据,可以将其看作是一个个的键值对 使用get方法可以通过key拿到值,如果该值是一个列表的话,get方法只能拿到列表的最后一个值,使用ge ...
- MATLAB探索初步问题汇总
MATLAB命令窗口如果显示:尝试将SCRIPT normrnd作为函数执行:C:\User-- 出错sort 这类问题,一般是你的*.m文件的名与内置函数名重名,改一下文件名即可. 2.MATLAB ...
- 分布式 PostgreSQL 集群(Citus)官方安装指南
单节点 Citus Docker (Mac 与 Linux) Docker 镜像仅用于开发/测试目的, 并且尚未准备好用于生产用途. 您可以使用一个命令在 Docker 中启动 Citus: # st ...
- 使用SymPy
最近工作的原因,需要进行一些积分运算,通过一些搜索得知了SymPy,记录一下使用历程. 1. SymPy介绍 SymPy是关于Symbolic Mathematics的Python库,它旨在成为一个功 ...
- kubernetes更改coredns增加解析
kubernetes更改coredns增加解析 k8s中coredns可以为全集群提供dns解析功能, 所以如果我们要手动增加dns解析, 只需在coredns中增加dns解析对即可 1. 编辑cor ...