js中的class

Posted Frank-Link

tags:

篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了js中的class相关的知识,希望对你有一定的参考价值。

概述

在ES6中,class (类)作为对象的模板被引入,可以通过 class 关键字定义类。class 的本质是 function。它可以看作一个语法糖,让对象原型的写法更加清晰、更像面向对象编程的语法。

重点在于构造函数,使用的是构造函数来模拟类。

类的声明

声明一个类,需要使用class关键字

// 正常声明一个类
class Rectangle {
  constructor(height, width) {
    this.height = height;
    this.width = width;
  }
}
// 匿名一个类
let Rectangle1 = class {
  constructor(height, width) {
    this.height = height;
    this.width = width;
  }
}
// 具名一个类
let Rectangle2 = class Rectangle {
  constructor(height, width) {
    this.height = height;
    this.width = width;
  }
}

注意,和函数声明的最大的区别在于,类声明不会出现声明提前。

当然,类也不允许重复声明

class Example1{}
class Example1{}
// Uncaught SyntaxError: Identifier ‘Example‘ has already been declared

let Example2 = class{}
class Example2{}
// Uncaught SyntaxError: Identifier ‘Example2‘ has already been declared

类的主体

prototype

ES6 中,prototype 仍旧存在,虽然可以直接自类中定义方法,但是其实方法还是定义在 prototype 上的。 我们可以使用它为已存在的类覆盖方法 / 初始化时添加方法

// 声明一个类
class Example3 {
  say() {
    console.log(‘hi Class !‘)
  }
}
// 类的方法被覆盖了 - Chrome80版本,覆盖无效
Example3.prototype = {
  say() {
    console.log(‘hello Class !‘)
  }
}
// 为类添加方法
Object.asign(Example.prototype, {
  listen() {
    console.log(‘hello !‘)
  }
})
// 删除类上的方法
Reflect.deleteProperty(Example3.prototype, ‘say‘)

static

静态属性,class本身的属性,即直接定义在类内部的属性( Class.propname ),不需要实例化。 ES6 中规定,Class 内部只有静态方法,没有静态属性。

// 声明一个带有静态属性的类
class Example4 {
  static a = 1
}
// 类本身可以直接调用
Example4.a // 1

通过new 关键字生成的对象,无法调用该方法

class Point {
  constructor(x, y) {
    this.x = x
    this.y = y
  }

  static distance(a, b) {
    const dx = a.x - b.x
    const dy = a.y - b.y
    return Math.hypot(dx, dy) // 毕达哥拉斯定理
  }
}

const p1 = new Point(5, 5)
const p2 = new Point(10, 10)
console.log(Point.distance(p1, p2))

上方的p1, p2对象中找不到静态方法distance

console.log(p3) // Point?{x: 5, y: 5}
console.log(p4) // Point?{x: 10, y: 10}

声明一个类之后,可以使用它新建一个对象

let rectAngle = new Rectangle

该对象具有constructor方法

name

该属性能获取或者返回class的类名

let Example5 = class Exam {
  a = 1
  constructor() {
    console.log(this.a)
  }
}
console.log(Example5.name) // Exam

let Example6 = class {
  a = 2
  constructor() {
    console.log(this.a)
  }
}
console.log(Example6.name) // Example6

constructor

该方法是类的默认方法,创建类的实例化对象时被调用

class Rectangle {
  // 构造函数
  constructor(height, width) {
    this.height = height
    this.width = width
    console.log(‘我是constructor‘)
  }

  // get 方法会在对象创建后立即调用并返回调用结果
  get area() {
    return this.calcArea()
  }

  // 定义calcArea函数
  calcArea() {
    return this.height * this.width
  }
}

使用被声明的类

const square = new Rectangle(10, 10) // ‘我是constructor‘
console.log(square.area) // 100

constructor没有返回值时,默认返回实例化对象this,其原型是当前的Class

console.log(square instanceof Rectangle) // true

constructor指定返回值时,返回被指定的对象,其原型是被指向对象的原型

class Example7 {
  constructor() {
    // 指定返回值
    return new Rectangle()
  }
}
console.log(new Example7() instanceof Example7) // false
console.log(new Example7() instanceof Rectangle) // true

静态方法、原型方法与实例方法

// 静态
class StaticFunc {
  static sum(a, b) {
    console.log(a + b)
  }
}
// 调用方式
StaticFunc.sum(1, 2) // 3

// 原型
class PrototypeFunc {
  sum(a, b) {
    console.log(a + b)
  }
}
const protoFunc = new PrototypeFunc()
protoFunc.sum(1, 2) // 3

// 实例
class InstanceFunc {
  constructor() {
    this.sum = (a, b) => {
      console.log(a + b)
    }
  }
}
// 实例化时被调用,为实例化对象增加方法
const instanceFunc = new InstanceFunc()
instanceFunc.sum(1, 2) // 3

extends

使用extends关键字创建子类

class Animal {
  constructor(name) {
    this.name = name
  }

  // 类中创建的函数,可以省略function关键字
  speck() {
    console.log(this.name)
  }
}

// 创建Animal的子类 - 子类拥有父类的全部方法,还拥有私有方法
class Dog extends Animal {
  // 父类不存在的私有方法
  listen() {
    console.log(this.name)
  }
}

let d = new Dog(‘Turkey‘)
d.speck() // ‘Turkey‘
d.listen() // ‘Turkey‘

super

使用super调用超类

class Cat {
  constructor(name) {
    this.name = name
  }

  speck() {
    console.log(this.name)
  }
}

class Lion extends Cat {
  listen() {
    super.speck()
  }
}
let l = new Lion(‘Mickey‘)
l.speck() // ‘Mickey‘
l.listen() // ‘Mickey‘

参考

以上是关于js中的class的主要内容,如果未能解决你的问题,请参考以下文章

VSCode自定义代码片段9——JS中的面向对象编程

关于js----------------分享前端开发常用代码片段

Chrome-Devtools代码片段中的多个JS库

Node.js JavaScript 片段中的跳过代码

XSS:如何从 C# 中的字符串中删除 JS 片段?

JavaScript笔试题(js高级代码片段)