Classes are a template for creating objects. They encapsulate data with code to work on that data. Classes in JS are built on prototypes but also have some syntax and semantics that are not shared with ES5 classalike semantics.

Defining classes

Classes are in fact "special functions ", and just as you can define function expressions and 函数声明 , the class syntax has two components: class expressions and class declarations .

Class declarations

One way to define a class is using a class declaration . To declare a class, you use the class keyword with the name of the class ("Rectangle" here).

class Rectangle {
  constructor(height, width) {
    this.height = height;
    this.width = width;
  }
}
					

Hoisting

An important difference between 函数声明 and class declarations is that function declarations are hoisted and class declarations are not. You first need to declare your class and then access it, otherwise code like the following will throw a ReferenceError :

const p = new Rectangle(); // ReferenceError
class Rectangle {}
					

Class expressions

A class expression is another way to define a class. Class expressions can be named or unnamed. The name given to a named class expression is local to the class's body. (it can be retrieved through the class's (not an instance's) name property, though).

// unnamed
let Rectangle = class {
  constructor(height, width) {
    this.height = height;
    this.width = width;
  }
};
console.log(Rectangle.name);
// output: "Rectangle"
// named
let Rectangle = class Rectangle2 {
  constructor(height, width) {
    this.height = height;
    this.width = width;
  }
};
console.log(Rectangle.name);
// output: "Rectangle2"
					

注意: Class expressions are subject to the same hoisting restrictions as described in the Class declarations 章节。

Class body and method definitions

The body of a class is the part that is in curly brackets {} . This is where you define class members, such as methods or constructor.

严格模式

The body of a class is executed in 严格模式 , i.e., code written here is subject to stricter syntax for increased performance, some otherwise silent errors will be thrown, and certain keywords are reserved for future versions of ECMAScript.

构造函数

constructor method is a special method for creating and initializing an object created with a class . There can only be one special method with the name "constructor" in a class. A SyntaxError will be thrown if the class contains more than one occurrence of a 构造函数 方法。

A constructor can use the super keyword to call the constructor of the super class.

Prototype methods

另请参阅 method definitions .

class Rectangle {
  constructor(height, width) {
    this.height = height;
    this.width = width;
  }
  // Getter
  get area() {
    return this.calcArea();
  }
  // Method
  calcArea() {
    return this.height * this.width;
  }
}
const square = new Rectangle(10, 10);
console.log(square.area); // 100
					

静态方法

static keyword defines a static method for a class. Static methods are called without instantiating their class and cannot be called through a class instance. Static methods are often used to create utility functions for an application.

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);
p1.distance; //undefined
p2.distance; //undefined
console.log(Point.distance(p1, p2)); // 7.0710678118654755
					

Binding this with prototype and static methods

When a static or prototype method is called without a value for this , such as by assigning a variable to the method and then calling it, the this value will be undefined inside the method. This behavior will be the same even if the "use strict" directive isn't present, because code within the class body's syntactic boundary is always executed in strict mode.

class Animal {
  speak() {
    return this;
  }
  static eat() {
    return this;
  }
}
let obj = new Animal();
obj.speak(); // the Animal object
let speak = obj.speak;
speak(); // undefined
Animal.eat() // class Animal
let eat = Animal.eat;
eat(); // undefined
					

If we rewrite the above using traditional function-based syntax in non–strict mode, then this method calls is automatically bound to the initial this value, which by default is the 全局对象 . In strict mode, autobinding will not happen; the value of this remains as passed.

function Animal() { }
Animal.prototype.speak = function() {
  return this;
}
Animal.eat = function() {
  return this;
}
let obj = new Animal();
let speak = obj.speak;
speak(); // global object (in non–strict mode)
let eat = Animal.eat;
eat(); // global object (in non-strict mode)
					

实例特性

Instance properties must be defined inside of class methods:

class Rectangle {
  constructor(height, width) {
    this.height = height;
    this.width = width;
  }
}
					

Static (class-side) data properties and prototype data properties must be defined outside of the ClassBody declaration:

Rectangle.staticWidth = 20;
Rectangle.prototype.prototypeWidth = 25;
					

Field declarations

Public and private field declarations are an experimental feature (stage 3) proposed at TC39 , the JavaScript standards committee. Support in browsers is limited, but the feature can be used through a build step with systems like Babel .

Public field declarations

With the JavaScript field declaration syntax, the above example can be written as:

class Rectangle {
  height = 0;
  width;
  constructor(height, width) {
    this.height = height;
    this.width = width;
  }
}
					

By declaring fields up-front, class definitions become more self-documenting, and the fields are always present.

As seen above, the fields can be declared with or without a default value.

public class fields 了解更多信息。

Private field declarations

Using private fields, the definition can be refined as below.

class Rectangle {
  #height = 0;
  #width;
  constructor(height, width) {
    this.#height = height;
    this.#width = width;
  }
}
					

It's an error to reference private fields from outside of the class; they can only be read or written within the class body. By defining things which are not visible outside of the class, you ensure that your classes' users can't depend on internals, which may change version to version.

Private fields can only be declared up-front in a field declaration.

Private fields cannot be created later through assigning to them, the way that normal properties can.

更多信息,见 private class fields .

Sub classing with extends

extends keyword is used in class declarations or class expressions to create a class as a child of another class.

class Animal {
  constructor(name) {
    this.name = name;
  }
  speak() {
    console.log(`${this.name} makes a noise.`);
  }
}
class Dog extends Animal {
  constructor(name) {
    super(name); // call the super class constructor and pass in the name parameter
  }
  speak() {
    console.log(`${this.name} barks.`);
  }
}
let d = new Dog('Mitzie');
d.speak(); // Mitzie barks.
					

If there is a constructor present in the subclass, it needs to first call super() before using "this".

One may also extend traditional function-based "classes":

function Animal (name) {
  this.name = name;
}
Animal.prototype.speak = function () {
  console.log(`${this.name} makes a noise.`);
}
class Dog extends Animal {
  speak() {
    console.log(`${this.name} barks.`);
  }
}
let d = new Dog('Mitzie');
d.speak(); // Mitzie barks.
// For similar methods, the child's method takes precedence over parent's method
					

Note that classes cannot extend regular (non-constructible) objects. If you want to inherit from a regular object, you can instead use Object.setPrototypeOf() :

const Animal = {
  speak() {
    console.log(`${this.name} makes a noise.`);
  }
};
class Dog {
  constructor(name) {
    this.name = name;
  }
}
// If you do not do this you will get a TypeError when you invoke speak
Object.setPrototypeOf(Dog.prototype, Animal);
let d = new Dog('Mitzie');
d.speak(); // Mitzie makes a noise.
					

Species

You might want to return Array objects in your derived array class MyArray . The species pattern lets you override default constructors.

For example, when using methods such as map() that returns the default constructor, you want these methods to return a parent Array object, instead of the MyArray object. The Symbol.species symbol lets you do this:

class MyArray extends Array {
  // Overwrite species to the parent Array constructor
  static get [Symbol.species]() { return Array; }
}
let a = new MyArray(1,2,3);
let mapped = a.map(x => x * x);
console.log(mapped instanceof MyArray); // false
console.log(mapped instanceof Array);   // true
					

Super class calls with super

super keyword is used to call corresponding methods of super class. This is one advantage over prototype-based inheritance.

class Cat {
  constructor(name) {
    this.name = name;
  }
  speak() {
    console.log(`${this.name} makes a noise.`);
  }
}
class Lion extends Cat {
  speak() {
    super.speak();
    console.log(`${this.name} roars.`);
  }
}
let l = new Lion('Fuzzy');
l.speak();
// Fuzzy makes a noise.
// Fuzzy roars.
					

Mix-ins

Abstract subclasses or mix-ins are templates for classes. An ECMAScript class can only have a single superclass, so multiple inheritance from tooling classes, for example, is not possible. The functionality must be provided by the superclass.

A function with a superclass as input and a subclass extending that superclass as output can be used to implement mix-ins in ECMAScript:

let calculatorMixin = Base => class extends Base {
  calc() { }
};
let randomizerMixin = Base => class extends Base {
  randomize() { }
};
					

A class that uses these mix-ins can then be written like this:

class Foo { }
class Bar extends calculatorMixin(randomizerMixin(Foo)) { }
					

规范

规范
ECMAScript (ECMA-262)
The definition of 'Class definitions' in that specification.

浏览器兼容性

The compatibility table on this page is generated from structured data. If you'd like to contribute to the data, please check out https://github.com/mdn/browser-compat-data and send us a pull request. 更新 GitHub 上的兼容性数据
Desktop Mobile Server
Chrome Edge Firefox Internet Explorer Opera Safari Android webview Chrome for Android Firefox for Android Opera for Android Safari on iOS Samsung Internet Node.js
Chrome 49
49
不支持 42 — 49
Strict mode is required.
不支持 42 — 49 Disabled
Disabled ). To change preferences in Chrome, visit
Edge 13 Firefox 45 IE No Opera 36
36
不支持 29 — 36
Strict mode is required.
不支持 29 — 36 Disabled
Disabled From version 29 until version 36 (exclusive): this feature is behind the Experimental JavaScript preference (needs to be set to Enabled ).
Safari 9 WebView Android 49
49
不支持 42 — 49
Strict mode is required.
Chrome Android 49
49
不支持 42 — 49
Strict mode is required.
不支持 42 — 49 Disabled
Disabled ). To change preferences in Chrome, visit
Firefox Android 45 Opera Android 36
36
不支持 29 — 36
Strict mode is required.
不支持 29 — 36 Disabled
Disabled From version 29 until version 36 (exclusive): this feature is behind the Experimental JavaScript preference (needs to be set to Enabled ).
Safari iOS 9 Samsung Internet Android 5.0
5.0
不支持 4.0 — 5.0
Strict mode is required.
nodejs 6.0.0
6.0.0
4.0.0 Disabled
Disabled From version 4.0.0: this feature is behind the --use_strict runtime flag.
5.0.0 Disabled
Disabled From version 5.0.0: this feature is behind the --harmony runtime flag.
构造函数 Chrome 49
49
不支持 42 — 49
Strict mode is required.
不支持 42 — 49 Disabled
Disabled ). To change preferences in Chrome, visit
Edge 13 Firefox 45 IE No Opera 36
36
不支持 29 — 36
Strict mode is required.
不支持 29 — 36 Disabled
Disabled From version 29 until version 36 (exclusive): this feature is behind the Experimental JavaScript preference (needs to be set to Enabled ).
Safari 9 WebView Android 49
49
不支持 42 — 49
Strict mode is required.
Chrome Android 49
49
不支持 42 — 49
Strict mode is required.
不支持 42 — 49 Disabled
Disabled ). To change preferences in Chrome, visit
Firefox Android 45 Opera Android 36
36
不支持 29 — 36
Strict mode is required.
不支持 29 — 36 Disabled
Disabled From version 29 until version 36 (exclusive): this feature is behind the Experimental JavaScript preference (needs to be set to Enabled ).
Safari iOS 9 Samsung Internet Android 5.0
5.0
不支持 4.0 — 5.0
Strict mode is required.
nodejs 6.0.0
6.0.0
4.0.0 Disabled
Disabled From version 4.0.0: this feature is behind the --use_strict runtime flag.
5.0.0 Disabled
Disabled From version 5.0.0: this feature is behind the --harmony runtime flag.
extends Chrome 49
49
不支持 42 — 49
Strict mode is required.
不支持 42 — 49 Disabled
Disabled ). To change preferences in Chrome, visit
Edge 13 Firefox 45 IE No Opera 36
36
不支持 29 — 36
Strict mode is required.
不支持 29 — 36 Disabled
Disabled From version 29 until version 36 (exclusive): this feature is behind the Experimental JavaScript preference (needs to be set to Enabled ).
Safari 9 WebView Android 49
49
不支持 42 — 49
Strict mode is required.
Chrome Android 49
49
不支持 42 — 49
Strict mode is required.
不支持 42 — 49 Disabled
Disabled ). To change preferences in Chrome, visit
Firefox Android 45 Opera Android 36
36
不支持 29 — 36
Strict mode is required.
不支持 29 — 36 Disabled
Disabled From version 29 until version 36 (exclusive): this feature is behind the Experimental JavaScript preference (needs to be set to Enabled ).
Safari iOS 9 Samsung Internet Android 5.0
5.0
不支持 4.0 — 5.0
Strict mode is required.
nodejs 6.0.0
6.0.0
4.0.0 Disabled
Disabled From version 4.0.0: this feature is behind the --use_strict runtime flag.
5.0.0 Disabled
Disabled From version 5.0.0: this feature is behind the --harmony runtime flag.
Private class fields Chrome 74 Edge 79 Firefox No IE No Opera 62 Safari 14 WebView Android 74 Chrome Android 74 Firefox Android No Opera Android 53 Safari iOS 14 Samsung Internet Android No nodejs 12.0.0
Public class fields Chrome 72 Edge 79 Firefox 69 IE No Opera 60 Safari 14 WebView Android 72 Chrome Android 72 Firefox Android No Opera Android 51 Safari iOS 14 Samsung Internet Android No nodejs 12.0.0
static Chrome 49
49
不支持 42 — 49
Strict mode is required.
不支持 42 — 49 Disabled
Disabled ). To change preferences in Chrome, visit
Edge 13 Firefox 45 IE No Opera 36
36
不支持 29 — 36
Strict mode is required.
不支持 29 — 36 Disabled
Disabled From version 29 until version 36 (exclusive): this feature is behind the Experimental JavaScript preference (needs to be set to Enabled ).
Safari 9 WebView Android 49
49
不支持 42 — 49
Strict mode is required.
Chrome Android 49
49
不支持 42 — 49
Strict mode is required.
不支持 42 — 49 Disabled
Disabled ). To change preferences in Chrome, visit
Firefox Android 45 Opera Android 36
36
不支持 29 — 36
Strict mode is required.
不支持 29 — 36 Disabled
Disabled From version 29 until version 36 (exclusive): this feature is behind the Experimental JavaScript preference (needs to be set to Enabled ).
Safari iOS 9 Samsung Internet Android 5.0
5.0
不支持 4.0 — 5.0
Strict mode is required.
nodejs 6.0.0
6.0.0
4.0.0 Disabled
Disabled From version 4.0.0: this feature is behind the --use_strict runtime flag.
5.0.0 Disabled
Disabled From version 5.0.0: this feature is behind the --harmony runtime flag.
Static class fields Chrome 72 Edge 79 Firefox 75 IE No Opera 60 Safari No WebView Android 72 Chrome Android 72 Firefox Android No Opera Android 51 Safari iOS No Samsung Internet Android No nodejs 12.0.0

图例

完整支持

完整支持

不支持

不支持

见实现注意事项。

用户必须明确启用此特征。

用户必须明确启用此特征。

Re-running a class definition

A class can't be redefined. Attempting to do so produces a SyntaxError .

If you're experimenting with code in a web browser, such as the Firefox Web Console ( 工具 > Web Developer > Web 控制台 ) and you 'Run' a definition of a class with the same name twice, you'll get a SyntaxError: redeclaration of let ClassName ; . (See further discussion of this issue in bug 1428672 .) Doing something similar in Chrome Developer Tools gives you a message like Uncaught SyntaxError: Identifier ' ClassName ' has already been declared at <anonymous>:1:1 .

另请参阅

元数据

  • 最后修改:
  1. JavaScript
  2. 教程:
  3. 完全初学者
    1. JavaScript 基础
    2. JavaScript 第一步
    3. JavaScript 构建块
    4. 引入 JavaScript 对象
  4. JavaScript 指南
    1. 介绍
    2. 语法和类型
    3. 控制流程和错误处理
    4. 循环和迭代
    5. 函数
    6. 表达式和运算符
    7. 数字和日期
    8. 文本格式化
    9. 正则表达式
    10. 索引集合
    11. 键控集合
    12. Working with objects
    13. 对象模型的细节
    14. Using promises
    15. 迭代器和生成器
    16. Meta programming
    17. JavaScript 模块
  5. 中间体
    1. Client-side JavaScript frameworks
    2. 客户端侧 Web API
    3. 重新介绍 JavaScript
    4. JavaScript 数据结构
    5. 相等比较和相同
    6. 闭包
  6. 高级
    1. 继承和原型链
    2. 严格模式
    3. JavaScript 类型数组
    4. 内存管理
    5. 并发模型和事件循环
  7. 参考:
  8. 内置对象
    1. AggregateError
    2. Array
    3. ArrayBuffer
    4. AsyncFunction
    5. Atomics
    6. BigInt
    7. BigInt64Array
    8. BigUint64Array
    9. 布尔
    10. DataView
    11. Date
    12. Error
    13. EvalError
    14. FinalizationRegistry
    15. Float32Array
    16. Float64Array
    17. Function
    18. Generator
    19. GeneratorFunction
    20. Infinity
    21. Int16Array
    22. Int32Array
    23. Int8Array
    24. InternalError
    25. Intl
    26. JSON
    27. Map
    28. Math
    29. NaN
    30. Number
    31. Object
    32. Promise
    33. Proxy
    34. RangeError
    35. ReferenceError
    36. Reflect
    37. RegExp
    38. Set
    39. SharedArrayBuffer
    40. String
    41. Symbol
    42. SyntaxError
    43. TypeError
    44. TypedArray
    45. URIError
    46. Uint16Array
    47. Uint32Array
    48. Uint8Array
    49. Uint8ClampedArray
    50. WeakMap
    51. WeakRef
    52. WeakSet
    53. WebAssembly
    54. decodeURI()
    55. decodeURIComponent()
    56. encodeURI()
    57. encodeURIComponent()
    58. escape()
    59. eval()
    60. globalThis
    61. isFinite()
    62. isNaN()
    63. null
    64. parseFloat()
    65. parseInt()
    66. undefined
    67. unescape()
    68. uneval()
  9. 表达式 & 运算符
    1. Addition (+)
    2. Addition assignment (+=)
    3. Assignment (=)
    4. Bitwise AND (&)
    5. Bitwise AND assignment (&=)
    6. Bitwise NOT (~)
    7. Bitwise OR (|)
    8. Bitwise OR assignment (|=)
    9. Bitwise XOR (^)
    10. Bitwise XOR assignment (^=)
    11. Comma operator (,)
    12. 条件 (三元) 运算符
    13. Decrement (--)
    14. Destructuring assignment
    15. Division (/)
    16. Division assignment (/=)
    17. Equality (==)
    18. Exponentiation (**)
    19. Exponentiation assignment (**=)
    20. 函数表达式
    21. Greater than (>)
    22. Greater than or equal (>=)
    23. Grouping operator ( )
    24. Increment (++)
    25. Inequality (!=)
    26. Left shift (<<)
    27. Left shift assignment (<<=)
    28. Less than (<)
    29. Less than or equal (<=)
    30. Logical AND (&&)
    31. Logical AND assignment (&&=)
    32. Logical NOT (!)
    33. Logical OR (||)
    34. Logical OR assignment (||=)
    35. Logical nullish assignment (??=)
    36. Multiplication (*)
    37. Multiplication assignment (*=)
    38. Nullish coalescing operator (??)
    39. 对象初始化器
    40. 运算符优先级
    41. Optional chaining (?.)
    42. Pipeline operator (|>)
    43. 特性访问器
    44. Remainder (%)
    45. Remainder assignment (%=)
    46. Right shift (>>)
    47. Right shift assignment (>>=)
    48. Spread syntax (...)
    49. Strict equality (===)
    50. Strict inequality (!==)
    51. Subtraction (-)
    52. Subtraction assignment (-=)
    53. Unary negation (-)
    54. Unary plus (+)
    55. Unsigned right shift (>>>)
    56. Unsigned right shift assignment (>>>=)
    57. 异步函数表达式
    58. await
    59. class expression
    60. delete operator
    61. function* 表达式
    62. in operator
    63. instanceof
    64. new operator
    65. new.target
    66. super
    67. this
    68. typeof
    69. void 运算符
    70. yield
    71. yield*
  10. 语句 & 声明
    1. async function
    2. block
    3. break
    4. class
    5. const
    6. continue
    7. debugger
    8. do...while
    9. empty
    10. export
    11. for
    12. for await...of
    13. for...in
    14. for...of
    15. 函数声明
    16. function*
    17. if...else
    18. import
    19. import.meta
    20. label
    21. let
    22. return
    23. switch
    24. throw
    25. try...catch
    26. var
    27. while
    28. with
  11. 函数
    1. 箭头函数表达式
    2. 默认参数
    3. 方法定义
    4. 其余参数
    5. 自变量对象
    6. getter
    7. setter
    1. Private class fields
    2. Public class fields
    3. 构造函数
    4. extends
    5. static
  12. 错误
    1. Error: Permission denied to access property "x"
    2. InternalError: too much recursion
    3. RangeError: argument is not a valid code point
    4. RangeError: invalid array length
    5. RangeError: invalid date
    6. RangeError: precision is out of range
    7. RangeError: radix must be an integer
    8. RangeError: repeat count must be less than infinity
    9. RangeError: repeat count must be non-negative
    10. ReferenceError: "x" is not defined
    11. ReferenceError: assignment to undeclared variable "x"
    12. ReferenceError: can't access lexical declaration`X' before initialization
    13. ReferenceError: deprecated caller or arguments usage
    14. ReferenceError: invalid assignment left-hand side
    15. ReferenceError: reference to undefined property "x"
    16. SyntaxError: "0"-prefixed octal literals and octal escape seq. are deprecated
    17. SyntaxError: "use strict" not allowed in function with non-simple parameters
    18. SyntaxError: "x" is a reserved identifier
    19. SyntaxError: JSON.parse: bad parsing
    20. SyntaxError: Malformed formal parameter
    21. SyntaxError: Unexpected token
    22. SyntaxError: Using //@ to indicate sourceURL pragmas is deprecated. Use //# instead
    23. SyntaxError: a declaration in the head of a for-of loop can't have an initializer
    24. SyntaxError: applying the 'delete' operator to an unqualified name is deprecated
    25. SyntaxError: for-in loop head declarations may not have initializers
    26. SyntaxError: function statement requires a name
    27. SyntaxError: identifier starts immediately after numeric literal
    28. SyntaxError: illegal character
    29. SyntaxError: invalid regular expression flag "x"
    30. SyntaxError: missing ) after argument list
    31. SyntaxError: missing ) after condition
    32. SyntaxError: missing : after property id
    33. SyntaxError: missing ; before statement
    34. SyntaxError: missing = in const declaration
    35. SyntaxError: missing ] after element list
    36. SyntaxError: missing formal parameter
    37. SyntaxError: missing name after . operator
    38. SyntaxError: missing variable name
    39. SyntaxError: missing } after function body
    40. SyntaxError: missing } after property list
    41. SyntaxError: redeclaration of formal parameter "x"
    42. SyntaxError: return not in function
    43. SyntaxError: test for equality (==) mistyped as assignment (=)?
    44. SyntaxError: unterminated string literal
    45. TypeError: "x" has no properties
    46. TypeError: "x" is (not) "y"
    47. TypeError: "x" is not a constructor
    48. TypeError: "x" is not a function
    49. TypeError: "x" is not a non-null object
    50. TypeError: "x" is read-only
    51. TypeError: 'x' is not iterable
    52. TypeError: More arguments needed
    53. TypeError: Reduce of empty array with no initial value
    54. TypeError: X.prototype.y called on incompatible type
    55. TypeError: can't access dead object
    56. TypeError: can't access property "x" of "y"
    57. TypeError: can't assign to property "x" on "y": not an object
    58. TypeError: can't define property "x": "obj" is not extensible
    59. TypeError: can't delete non-configurable array element
    60. TypeError: can't redefine non-configurable property "x"
    61. TypeError: cannot use 'in' operator to search for 'x' in 'y'
    62. TypeError: cyclic object value
    63. TypeError: invalid 'instanceof' operand 'x'
    64. TypeError: invalid Array.prototype.sort argument
    65. TypeError: invalid arguments
    66. TypeError: invalid assignment to const "x"
    67. TypeError: property "x" is non-configurable and can't be deleted
    68. TypeError: setting getter-only property "x"
    69. TypeError: variable "x" redeclares argument
    70. URIError: malformed URI sequence
    71. Warning: -file- is being assigned a //# sourceMappingURL, but already has one
    72. Warning: 08/09 is not a legal ECMA-262 octal constant
    73. Warning: Date.prototype.toLocaleFormat is deprecated
    74. Warning: JavaScript 1.6's for-each-in loops are deprecated
    75. Warning: String.x is deprecated; use String.prototype.x instead
    76. Warning: expression closures are deprecated
    77. Warning: unreachable code after return statement
  13. 杂项
    1. JavaScript 技术概述
    2. 词法语法
    3. JavaScript 数据结构
    4. Enumerability and ownership of properties
    5. Iteration protocols
    6. 严格模式
    7. 过渡到严格模式
    8. 模板文字
    9. 弃用特征

Copyright  © 2014-2026 乐数软件    

工业和信息化部: 粤ICP备14079481号-1