le mie informazioni di contatto
Posta[email protected]
2024-07-12
한어Русский языкEnglishFrançaisIndonesianSanskrit日本語DeutschPortuguêsΕλληνικάespañolItalianoSuomalainenLatina
La classe in ES6 è uno zucchero sintattico per la programmazione orientata agli oggetti, che fornisce un modo conciso per definire la struttura e il comportamento degli oggetti.
Nel linguaggio JavaScript, il modo tradizionale per generare oggetti istanza è tramite i costruttori. Di seguito è riportato un esempio.
function Point(x, y) {
this.x = x;
this.y = y;
}
Point.prototype.toString = function () {
return '(' + this.x + ', ' + this.y + ')';
};
var p = new Point(1, 2);
Fondamentalmente, la classe ES6 può essere considerata solo uno zucchero sintattico. La maggior parte delle sue funzioni possono essere eseguite da ES5. Il nuovo metodo di scrittura della classe rende solo il metodo di scrittura del prototipo di oggetto più chiaro e più simile alla sintassi della programmazione orientata agli oggetti. Il codice precedente viene riscritto utilizzando le classi ES6, come segue:
class Point {
constructor(x, y) {
this.x = x;
this.y = y;
}
toString() {
return '(' + this.x + ', ' + this.y + ')';
}
}
Le classi ES6 possono essere considerate come un altro modo di scrivere costruttori:
class Point {
// ...
}
typeof Point // "function"
Point === Point.prototype.constructor // true
----------------------------------------------------------------------------
class Point {
constructor() {
// ...
}
toString() {
// ...
}
toValue() {
// ...
}
}
// 等同于
Point.prototype = {
constructor() {},
toString() {},
toValue() {},
};
1. Sintassi dichiarativa: utilizza la parola chiave class per dichiarare una classe.
2. Costruttore: utilizza il metodo del costruttore per inizializzare un'istanza di classe.
3. Metodi di istanza: un metodo comune definito all'interno di una classe, utilizzalo per accedere alle proprietà dell'istanza.
4. Metodi statici: Definito utilizzando la parola chiave static e non dipende dall'istanza della classe.
5. Proprietà dell'istanza: inizializza nel costruttore o utilizza la sintassi della dichiarazione del campo (attualmente una proposta della Fase 3).
6. Eredità: implementato utilizzando la parola chiave extends.
7. super parola chiave: chiama il costruttore o il metodo della classe genitore nel costruttore della sottoclasse.
8. getter e setter: utilizzare get e set per definire le funzioni di accesso per le proprietà.
9. Proprietà e metodi privati: utilizzare # per definire proprietà e metodi privati (attualmente una proposta della Fase 3).
1. Definizione e istanziazione di classi di base
class Point {
constructor(x, y) {
this.x = x;
this.y = y;
}
toString() {
return `Point(${this.x}, ${this.y})`;
}
}
let point = new Point(10, 20);
console.log(point.toString()); // 输出: Point(10, 20)
2. Metodi e proprietà statiche
class MathUtils {
constructor() {
console.log(MyClass.myStaticProp); // 42
}
static add(a, b) {
return a + b;
}
static myStaticProp = 42;
}
console.log(MathUtils.add(1, 2)); // 输出: 3
3. Eredità e super
class Rectangle {
constructor(width, height) {
this.width = width;
this.height = height;
}
area() {
return this.width * this.height;
}
}
class Square extends Rectangle {
constructor(sideLength) {
super(sideLength, sideLength);
}
}
let square = new Square(5);
console.log(square.area()); // 输出: 25
4. getter e setter
class Rectangle {
constructor(width, height) {
this.width = width;
this.height = height;
}
get area() {
return this.width * this.height;
}
set width(newWidth) {
if (newWidth > 0) {
this.width = newWidth;
} else {
console.log("Width must be positive.");
}
}
}
let rect = new Rectangle(4, 5);
console.log(rect.area); // 输出: 20
rect.width = -10; // 输出: Width must be positive.
(1) Modalità rigorosa
Internamente, le classi e i moduli sono in modalità rigorosa per impostazione predefinita, quindi non è necessario utilizzare use strict per specificare la modalità di esecuzione. Finché il codice è scritto in una classe o in un modulo, è disponibile solo la modalità rigorosa. Considerando che tutto il codice futuro verrà effettivamente eseguito in moduli, ES6 aggiorna effettivamente l'intero linguaggio alla modalità rigorosa.
(2) Non è prevista alcuna promozione
Le classi non hanno il sollevamento variabile (paranco), che è completamente diverso da ES5.
new Foo(); // ReferenceError
class Foo {}
//不会报错
//因为 Bar 继承 Foo 的时候, Foo 已经有定义了。
//但是,如果存在 class 的提升,上面代码就会报错,
//因为 class 会被提升到代码头部,而 let 命令是不提升的,
//所以导致 Bar 继承 Foo 的时候, Foo 还没有定义。
{
let Foo = class {};
class Bar extends Foo {
}
}
(3) attributo nome
Poiché in sostanza una classe ES6 è solo un wrapper per il costruttore ES5, molte funzionalità della funzione vengono ereditate da Class, incluso l'attributo name.
class Point {}
Point.name // "Point"
//name 属性总是返回紧跟在 class 关键字后面的类名。
(4) Metodo del generatore
Se un metodo è preceduto da un asterisco (*), significa che il metodo è una funzione Generator.
class Foo {
constructor(...args) {
this.args = args;
}
* [Symbol.iterator]() {
for (let arg of this.args) {
yield arg;
}
}
}
for (let x of new Foo('hello', 'world')) {
console.log(x);
}
// hello
// world
//Foo 类的 Symbol.iterator 方法前有一个星号,表示该方法是一个 Generator 函数。
//Symbol.iterator 方法返回一个 Foo 类的默认遍历器, for...of 循环会自动调用这个遍历器。
(5) Il punto di questo
Se un metodo di classe lo contiene, punta a un'istanza della classe per impostazione predefinita. Bisogna però fare molta attenzione, poiché questo metodo potrebbe causare errori se utilizzato da solo.
class Logger {
printName(name = 'there') {
this.print(`Hello ${name}`);
}
print(text) {
console.log(text);
}
}
const logger = new Logger();
const { printName } = logger;
printName(); // TypeError: Cannot read property 'print' of undefined
Evita di usarlo, collegalo nel costruttore:
class Logger {
constructor() {
this.printName = this.printName.bind(this);
}
// ...
}
Evita di usarlo, usa le funzioni freccia:
class Obj {
constructor() {
this.getThis = () => this;
}
}
const myObj = new Obj();
myObj.getThis() === myObj // true
Evita di usarlo, usa Proxy
function selfish (target) {
const cache = new WeakMap();
const handler = {
get (target, key) {
const value = Reflect.get(target, key);
if (typeof value !== 'function') {
return value;
}
if (!cache.has(value)) {
cache.set(value, value.bind(target));
}
return cache.get(value);
}
};
const proxy = new Proxy(target, handler);
return proxy;
}
const logger = selfish(new Logger());