Являются ли стрелки более быстрыми (более эффективными, светлее), чем обычная декларация автономной функции в v8?

Я задаю этот вопрос, потому что у меня и моего коллеги есть спор о стиле кодирования, потому что он предпочитает объявление функции стрелок:

const sum = (a, b) => a + b;

И я предпочитаю объявление автономной функции старого стиля:

function sum(a, b) {
    return a + b;
}

Моя точка зрения заключается в том, что код в старом стиле более читабельен, и вы можете более четко различать объявления функций и переменных. Его точка зрения заключается в том, что код со стрелками работает быстрее.

Знаете ли вы что-то о фактических штрафных санкциях (в версии 8), когда вместо функций стрелок вы используете декларацию автономной функции старого стиля? Действительно ли эти штрафы существуют?

Ответ 1

Разработчик V8 здесь. Функции со стрелками (в основном) являются просто "синтаксическим сахаром" для обычных объявлений функций. Там нет разницы в производительности.

Ответ 2

Ниже показано, что:

  • Существует штраф за первый (традиционный или жирный)
  • В Chrome нет заметной разницы.

function goFat() {
    for (var i = 0; i < 1000000; i++) {
        var v = ()=>{};
        v();
    }
}

function goTraditional() {
    for (var i = 0; i < 1000000; i++) {
        var v = function() {};
        v();
    }

}

function race() {
  var start = performance.now();
  goTraditional();
  console.log('Traditional elapsed: ' + (performance.now() - start));
  start = performance.now();
  goFat()
  console.log('Fat elapsed: ' + (performance.now() - start));
  start = performance.now();
  goTraditional();
  console.log('Traditional elapsed: ' + (performance.now() - start));
  start = performance.now();
  goFat()
  console.log('Fat elapsed: ' + (performance.now() - start));
  console.log('------');
}
<button onclick="race()">RACE!</button>

Ответ 3

В моем опыте я обнаружил, что функции стрелок работают быстрее, чем обычные функции JS. Вот небольшой фрагмент кода реагирования, который использует стрелку и нормальную функцию. Я обнаружил, что компонент, использующий функции стрелок, работает немного быстрее, чем компонент, имеющий обычную функцию js.

https://codepen.io/lokeshpathrabe/pen/qgzadx

class Fun extends React.Component {

  constructor(props){
    super(props);
    this.state = {start: new Date().getTime(),
                 end: new Date().getTime(),
                 number: 0};
    console.log('Function start: ', this.state.start);
    const fun = function(me){
      let n = me.state.number
      me.setState({
        ...me.state, end: new Date().getTime(), number: ++n
      })
    }
    this.interval = setInterval(fun, 1, this);
  }

  stop(){
    clearInterval(this.interval);
  }

  componentDidUpdate(){
    if((this.state.end - this.state.start) > 5000){
      console.log('Function end: ', this.state.end);
      clearInterval(this.interval)
    }
  }

  render() {
    return (
      <div>
        <h2>Counter with Function {this.state.number}</h2>
      </div>
    )
  }
}

class Arrow extends React.Component {

  constructor(props){
    super(props);
    this.state = {start: new Date().getTime(),
                 end: new Date().getTime(),
                 number: 0};
    console.log('Arrow start: ', this.state.start);
    this.interval = setInterval(()=>{
      let n = this.state.number
      this.setState({
        ...this.state, end: new Date().getTime(), number: ++n
      })
    }, 1);
  }

  stop(){
    clearInterval(this.interval);
  }

  componentDidUpdate(){
    if((this.state.end - this.state.start) > 5000){
      console.log('Arrow end: ', this.state.end);
      clearInterval(this.interval)
    }
  }

  render() {
    return (
      <div>
        <h2>Counter with Arrow {this.state.number}</h2>
      </div>
    )
  }
}

class HOC extends React.Component {

  render() {

    return (<div>
        <h1>The one reaching higher count wins</h1>
        <Arrow/>
        <Fun/>
        </div>);
  }
}

ReactDOM.render(<HOC />, document.getElementById('react-content'))

Дайте мне знать, если ваше мнение отличается

Ответ 4

Существует два примера для nodejs:

function testFat(a, b) {
    return a + b;
}

let testArrow = (a, b) => a + b;

let t1 = process.hrtime();
let tmp1 = 0;
for (let i = 0; i < 1000000000; ++i) {
    tmp1 = testFat(tmp1, i);
}
var fatTime = process.hrtime(t1);
console.log('fat', fatTime);

let t2 = process.hrtime();
let tmp2 = 0;
for (let i = 0; i < 1000000000; ++i) {
    tmp2 = testArrow(tmp2, i);
}
var arrowTime = process.hrtime(t2);
console.log('arrow', arrowTime);
function testFat() {
    return 0;
}

let testArrow = () => 0;

let t1 = process.hrtime();
for (let i = 0; i < 1000000000; ++i) {
    testFat();
}
var fatTime = process.hrtime(t1);
console.log('fat', fatTime);

let t2 = process.hrtime();
for (let i = 0; i < 1000000000; ++i) {
    testArrow();
}
var arrowTime = process.hrtime(t2);
console.log('arrow', arrowTime);'''

Результаты:

bash-3.2$ node test_plus_i.js

fat [ 0, 931986419 ]

arrow [ 0, 960479009 ]

bash-3.2$ node test_zero.js

fat [ 0, 479557888 ]

arrow [ 0, 478563661 ]

bash-3.2$ node --version

v12.8.0

bash-3.2$

Таким образом, вы можете видеть, что нет разницы в накладных расходах на вызовы функций.