Javascript ES2015(ES6)`class`语法提供了什么好处?

Javascript ES2015(ES6)`class`语法提供了什么好处?,javascript,ecmascript-6,Javascript,Ecmascript 6,我对ES6课程有很多疑问 使用class语法有什么好处?我读到公共/私有/静态将成为ES7的一部分,这是一个原因吗 此外,class是一种不同的OOP,还是它仍然是JavaScript的原型继承?我可以使用.prototype修改它吗?或者它只是同一个对象,但有两种不同的声明方式 有速度优势吗?如果您有像big app这样的大型应用程序,那么维护/理解它可能会更容易。ES6类是我们今天使用的原型类系统的语法糖。它们使您的代码更加简洁和自文档化,这是使用它们的充分理由(在我看来) 使用Babel传

我对ES6课程有很多疑问

使用
class
语法有什么好处?我读到公共/私有/静态将成为ES7的一部分,这是一个原因吗

此外,
class
是一种不同的OOP,还是它仍然是JavaScript的原型继承?我可以使用
.prototype
修改它吗?或者它只是同一个对象,但有两种不同的声明方式


有速度优势吗?如果您有像big app这样的大型应用程序,那么维护/理解它可能会更容易。

ES6类是我们今天使用的原型类系统的语法糖。它们使您的代码更加简洁和自文档化,这是使用它们的充分理由(在我看来)

使用Babel传输此ES6类:

class Foo {
  constructor(bar) {
    this._bar = bar;
  }

  getBar() {
    return this._bar;
  }
}
将为您提供如下信息:

var Foo = (function () {
  function Foo(bar) {    
    this._bar = bar;
  }

  Foo.prototype.getBar = function () {
    return this._bar;
  }

  return Foo;
})();
第二个版本并不复杂,需要维护的代码更多。当涉及到继承时,这些模式会变得更加复杂

因为这些类可以编译成我们一直使用的相同的原型模式,所以您可以对它们执行相同的原型操作。这包括在运行时添加方法等,访问
Foo.prototype.getBar
上的方法等

如今,ES6对隐私有一些基本的支持,尽管它基于不导出您不希望访问的对象。例如,您可以:

const BAR_NAME = 'bar';

export default class Foo {
  static get name() {
    return BAR_NAME;
  }
}
BAR\u NAME
将不可供其他模块直接参考

许多库都试图支持或解决这一问题,比如主干网及其
扩展
助手,它接受未经验证的方法类函数和属性散列,但是没有一个组合系统用于公开不涉及原型的原型继承

随着JS代码变得越来越复杂,代码库越来越大,我们已经开始发展很多模式来处理继承和模块之类的事情。用于为模块创建私有范围的IIFE有很多大括号和括号;缺少其中一个可能会导致执行完全不同的操作的有效脚本(在模块可以将下一个模块作为参数传递给它之后跳过分号,这很少是好的)


tl;dr:这是对我们已经做过的事情的补充,并在代码中明确了您的意图。

新的
语法目前主要是语法补充。(但是,你知道,这是一种很好的糖。)在ES2015-ES2020中,
没有什么比构造函数和
反射.构造
(包括子类化
错误
数组
更有效的了。(很可能在ES2021中,您可以使用
完成一些您无法完成的事情:,和。)

此外,
class
是一种不同的OOP,还是它仍然是JavaScript的原型继承

这与我们一直拥有的原型继承是一样的,只是如果您喜欢使用构造函数(
newfoo
,等等),语法更简洁、更方便。(特别是在从
数组
错误
派生的情况下,这在ES5和早期版本中是无法做到的。现在可以使用
反射.construct
[,],但不能使用旧的ES5样式。)

我可以使用
.prototype
修改它吗

是的,创建类后,仍然可以在类的构造函数上修改
prototype
对象。例如,这是完全合法的:

class Foo {
    constructor(name) {
        this.name = name;
    }
    
    test1() {
        console.log("test1: name = " + this.name);
    }
}
Foo.prototype.test2 = function() {
    console.log("test2: name = " + this.name);
};
有速度优势吗

通过为此提供一个特定的习惯用法,我认为引擎可能能够在优化方面做得更好。但是他们已经非常擅长优化了,我不认为会有显著的不同

ES2015(ES6)
class
syntax提供了什么好处

简而言之:如果您一开始不使用构造函数,则首选
Object.create
或类似的
class
对您没有用处

如果确实使用构造函数,则
类有一些好处:

  • 语法更简单,不易出错

  • 使用新语法设置继承层次结构要比使用旧语法容易得多(同样,也不容易出错)

  • 防止您因未能将
    new
    与构造函数一起使用而出现常见错误(如果
    不是构造函数的有效对象,则让构造函数引发异常)

  • 使用新语法调用父原型的方法版本要比旧语法简单得多(
    super.method()
    而不是
    ParentConstructor.prototype.method.call(this)
    Object.getPrototypeOf(Object.getPrototypeOf(this)).method.call(this)

下面是层次结构的语法比较:

// ***ES2015+**
class Person {
    constructor(first, last) {
        this.first = first;
        this.last = last;
    }

    personMethod() {
        // ...
    }
}

class Employee extends Person {
    constructor(first, last, position) {
        super(first, last);
        this.position = position;
    }

    employeeMethod() {
        // ...
    }
}

class Manager extends Employee {
    constructor(first, last, position, department) {
        super(first, last, position);
        this.department = department;
    }

    personMethod() {
        const result = super.personMethod();
        // ...use `result` for something...
        return result;
    }

    managerMethod() {
        // ...
    }
}
例如:

/***ES2015+**
班主任{
构造函数(第一个,最后一个){
this.first=first;
this.last=last;
}
人的方法(){
返回`Result from personMethod:this.first=${this.first},this.last=${this.last}`;
}
}
类雇员扩展个人{
建造师(第一、最后、位置){
超级(第一,最后);
这个位置=位置;
}
人的方法(){
const result=super.personMethod();
返回结果+`,this.position=${this.position}`;
}
雇员方法(){
// ...
}
}
类管理器扩展雇员{
建造师(第一、最后、职位、部门){
超级(第一、最后、位置);
这个部门=部门;
}
人的方法(){
const result=super.personMethod();
返回结果+`,this.department=${this.department}`;
}
管理方法(){
// ...
}
}
const m=新经理(“乔”、“布洛格斯”、“特殊项目经理”、“Cove”