JavaScript中的Classes

Posted by cl9000 on July 18, 2020

预测未来最好的方法就是去创造未来。——<亚伯拉罕·林肯>

作者:Ashish Lahoti
译者:cl9000
来源:https://codingnconcepts.com/javascript/classes-in-javascript/

类声明 Class Declaration

让我们看看在JavaScript中使用function构造函数class关键字创建类的例子:

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
// ES5 Function Constructor
function Car(brand, color, price) {
this.brand = brand;
this.color = color;
this.price = price;
}

// ES6 Class
class Car {
constructor(brand, color, price) {
this.brand = brand;
this.color = color;
this.price = price;
}
}

请注意,class是一种函数类型,所以我们用它来替换function。从这个意义上说,两种创建类的方法几乎是相同的。

我们可以让我们的代码更短,像这样:

1
2
3
4
5
class Car {
constructor(brand, color, price) {
Object.assign(this, { brand, color, price});
}
}

方法 Methods

让我们向 Car类 添加一些方法

  • Getter Setter方法(实例方法) 从类的实例中调用。它们分别使用 getset 关键字来定义,以获取和设置属性。
  • 原型方法(实例方法) 从类的实例中调用。它们用于访问实例属性并对它们执行一些操作。
  • 静态方法(类方法) 直接从类调用。它们是使用static关键字定义的,通常用于创建实用函数。
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
class Car {
constructor(brand, color, price) {
this._brand = brand;
this._color = color;
this._price = price;
}

// getter method
get color(){
return `color is ${this._color.toUpperCase()}`;
}

// setter method
set color(newColor){
this._color = newColor;
}

// prototype method
drive(){
return `driving ${this._brand} ${this._color} color car`;
}

// static method
static compareCars(car1, car2){
return `${car2._brand} is ${(car1._price > car2._price) ? "cheaper" : "costlier"} then ${car1._brand}`
}
}

让我们使用 Car 类创建一些对象,并调用它们的 getter、setter、prototype 和静态方法

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
let redToyotaCar = new Car("Toyota", "red", 500000);

console.log(redToyotaCar);
// prints Car {_brand: "Toyota", _color: "red", _price: 500000}

console.log(redToyotaCar.color);
// (getter method)
// prints 'color is RED'

console.log(redToyotaCar.drive());
// (prototype method)
// prints 'driving Toyota red color car'

redToyotaCar.color = "blue";
// (setter method)
// set color to blue

console.log(redToyotaCar.color);
// (getter method)
// prints 'color is BLUE'

console.log(redToyotaCar.drive());
// (prototype method)
// prints 'driving Toyota blue color car'

let blackAudiCar = new Car("Audi", "black", 900000);
console.log(Car.compareCars(redToyotaCar, blackAudiCar));
// (static method)
// prints 'Audi is costlier then Toyota'

在上面的类中,我们有color属性的 gettersetter。我们使用 _ convention来创建一个后备字段来存储我们的color属性。如果每次不调用getset,就会导致堆栈溢出。get将被调用,这将导致get被反复调用,从而创建一个无限循环。

VM172:12 Uncaught RangeError: Maximum call stack size exceeded
at Car.set color [as color] (:12:16)
at Car.set color [as color] (:12:16)
at Car.set color [as color] (:12:16)
at Car.set color [as color] (:12:16)
at Car.set color [as color] (:12:16)
at Car.set color [as color] (:12:16)
at Car.set color [as color] (:12:16)
at Car.set color [as color] (:12:16)
at Car.set color [as color] (:12:16)
at Car.set color [as color] (:12:16)

继承 Inheritance

假设我们想从Car类创建一个Toyota子类并添加一些额外的字段,如" model "" make "

1
2
3
4
5
6
7
8
9
class Toyota extends Car {
constructor(color, price, model, make){
super("Toyota", color, price);
Object.assign(this, {model, make});
}
drive(){
return `${super.drive()} made in ${this.make}`;
}
}

我们从Toyota子类中创建一些对象

1
2
3
4
5
6
7
8
9
10
let toyotaCamery = new Toyota("red", 800000, "Camary", 2010);

console.log(toyotaCamery);
// prints Toyota {_brand: "Toyota", _color: "red", _price: 800000, model: "Camary", make: 2010}

console.log(toyotaCamery.color);
// prints 'color is RED'

console.log(toyotaCamery.drive());
// prints 'driving Toyota red color car made in 2010'

我们看到,使用ES6 class关键字创建子类非常方便和容易。

参考

关注【公众号】,了解更多。
关注【公众号】,了解更多。
关注【公众号】,了解更多。



支付宝打赏 微信打赏

赞赏一下 坚持原创技术分享,您的支持将鼓励我继续创作!