tl; dr: Ні! Функції стрілки та декларації / вирази функцій не є еквівалентними і їх неможливо замінити наосліп.
Якщо функція , яку ви хочете замінити це НЕ використовувати this
, arguments
а не викликається new
, то так.
Як так часто: це залежить . Функції стрілки мають іншу поведінку, ніж декларації / вирази функцій, тому давайте розглянемо спочатку відмінності:
1. Лексичні this
таarguments
Функції стрілки не мають своєї власної this
або arguments
прив’язної. Натомість ці ідентифікатори розв’язуються в лексичній області, як і будь-яка інша змінна. Це означає, що всередині функції стрілки this
і arguments
відносяться до значень this
та arguments
в середовищі функція стрілки визначена в (тобто "зовні" функція стрілки):
// Example using a function expression
function createObject() {
console.log('Inside `createObject`:', this.foo);
return {
foo: 42,
bar: function() {
console.log('Inside `bar`:', this.foo);
},
};
}
createObject.call({foo: 21}).bar(); // override `this` inside createObject
// Example using a arrow function
function createObject() {
console.log('Inside `createObject`:', this.foo);
return {
foo: 42,
bar: () => console.log('Inside `bar`:', this.foo),
};
}
createObject.call({foo: 21}).bar(); // override `this` inside createObject
У випадку вираження функції this
посилається на об'єкт, який був створений всередині createObject
. У функції стрілка випадку, this
відноситься до this
про createObject
себе.
Це робить функції стрілок корисними, якщо вам потрібно отримати доступ this
до поточного середовища:
// currently common pattern
var that = this;
getData(function(data) {
that.data = data;
});
// better alternative with arrow functions
getData(data => {
this.data = data;
});
Зверніть увагу , що це також означає , що є НЕ можливо встановити стрілок функцію - й this
з .bind
або .call
.
Якщо ви не дуже знайомі this
, подумайте про читання
2. Функції стрілки не можна викликати new
ES2015 розрізняє функції, які можуть телефонувати, і функції, які можуть бути сконструйовані . Якщо функція constructable, вона може бути викликана з new
, тобто new User()
. Якщо функцію можна викликати, її можна викликати без new
(тобто звичайний виклик функції).
Функції, створені за допомогою оголошень / виразів функцій, можна конструювати і викликати.
Функції стрілки (та методи) можна телефонувати лише.
class
конструктори лише конструюються.
Якщо ви намагаєтеся викликати функцію, що не викликається, або побудувати функцію, яка не може бути сконструйована, ви отримаєте помилку виконання.
Знаючи це, ми можемо констатувати наступне.
Замінна:
- Функції , які не використовують
this
або arguments
.
- Функції, з якими використовується
.bind(this)
Не замінюється:
- Функції конструктора
- Функція / методи, додані до прототипу (тому що вони зазвичай використовують
this
)
- Варіатичні функції (якщо вони використовуються
arguments
(див. Нижче))
Давайте детальніше розглянемо це, використовуючи ваші приклади:
Функція конструктора
Це не буде працювати, оскільки функції стрілки не можна викликати new
. Продовжуйте використовувати декларацію / вираз функції або використовувати class
.
Методи прототипу
Швидше за все, ні, тому що способи прототипу зазвичай використовують this
для доступу до екземпляра. Якщо вони не використовуються this
, ви можете їх замінити. Однак якщо ви в першу чергу дбаєте про стислий синтаксис, використовуйте class
його стислий синтаксис методу:
class User {
constructor(name) {
this.name = name;
}
getName() {
return this.name;
}
}
Об'єктні методи
Аналогічно для методів в об'єкті буквально. Якщо метод хоче посилатися на сам об’єкт через this
, продовжуйте використовувати вирази функцій або використовуйте новий синтаксис методу:
const obj = {
getName() {
// ...
},
};
Відкликання дзвінків
Це залежить. Ви обов'язково повинні замінити його, якщо ви називаєте зовнішнє this
або використовуєте .bind(this)
:
// old
setTimeout(function() {
// ...
}.bind(this), 500);
// new
setTimeout(() => {
// ...
}, 500);
Але: Якщо код, який викликає зворотний виклик, явно встановлює this
певне значення, як це часто буває з обробниками подій, особливо з jQuery, і зворотний виклик використовує this
(або arguments
), ви не можете використовувати функцію стрілки!
Варіатичні функції
Оскільки функції стрілок не мають своїх власних arguments
, ви не можете просто замінити їх функцією стрілки. Однак ES2015 вводить альтернативу використанню arguments
: параметра відпочинку .
// old
function sum() {
let args = [].slice.call(arguments);
// ...
}
// new
const sum = (...args) => {
// ...
};
Питання, пов'язані з цим:
Подальші ресурси: