Ефективність Javascript: 'для' vs 'forEach' [закрито]


103

Який сучасний стандарт у 2017 році у Javascript з циклами for () vs .forEach.

Зараз я працюю свій шлях через Кольт Стіл «Web Dev Bootcamp» на Udemy і він виступає forEachнад forйого вченням. Однак я під час вправ шукав різні речі під час навчальних занять, і знаходжу все більше і більше рекомендацій, а не використовувати for-loop forEach. Здається, більшість людей констатують, що цикл for є більш ефективним.

Це щось, що змінилося з часу написання курсу (приблизно в 2015 році) чи це їхні плюси і мінуси для кожного, про що ви дізнаєтесь з більшим досвідом.

Будь-яка порада буде дуже вдячна.


11
Навіщо прив’язувати себе до чиєїсь суб’єктивної ідеї стандарту 2017 року? Прийміть позачасовий стандарт, наприклад, написання чистого, бездоганного коду, знаючи, що інженери наполегливо працюють над тим, щоб найбільш часто використовувані конструкції зробити дуже ефективними, а потім оптимізувати ефективність, коли у вас є конкретна проблема продуктивності

2
Уродженця forважко перемогти за чисту швидкість. forEach()викликає зворотний виклик для кожної ітерації; так, що очевидно несе з собою якусь накладну.
канон

1
будучи розробником, якого я навряд чи використовую або пропоную, більшу частину роботи виконують за допомогою методів карти, фільтрації або зменшення.
AT

12
@AT до тих пір, поки ви не з тих хлопців, хто використовує mapсуто для ітерації та відкидає новий масив, який він створює. Я не знаю, скільки людей мені довелося виправити лише на цьому конкретному виборі функції на цьому сайті.
канон

1
@canon погодився, вибір циклу важливий, і слід пам’ятати про результати та залишки таких методів під час вибору. Я вважаю, що для читабельності слід уникати звичайного "для петель".
AT

Відповіді:


200

для

forпетлі набагато ефективніші. Це циклічна конструкція, спеціально розроблена для повторення, тоді як умова є істинною , в той же час пропонує кроковий механізм (як правило, для збільшення ітератора). Приклад:

for (var i=0, n=arr.length; i < n; ++i ) {
   ...
}

Це не означає, що для -loops завжди буде ефективнішим, лише те, що JS-двигуни та браузери оптимізували їх таким чином. Протягом багатьох років виникали компроміси щодо того, яка конструкція циклічного циклу є більш ефективною (для, в той час, як зменшення, зворотний час тощо) - різні браузери та двигуни JS мають власні реалізації, які пропонують різні методики для отримання однакових результатів. Оскільки браузери додатково оптимізують відповідність вимогам продуктивності, теоретично це [].forEachможе бути реалізовано таким чином, щоб воно було швидшим або порівнянним з a for.

Переваги:

  • ефективний
  • дострокове припинення циклу (відзнаки breakта continue)
  • контроль стану ( i<nможе бути будь-яким, а не прив’язаним до розміру масиву)
  • змінне масштабування ( var iлистки iдоступні після закінчення циклу)

для кожного

.forEach- це методи, які в першу чергу ітераються над масивами (також над іншими переліченими, такими як Mapі Setоб'єкти). Вони новіші та надають код, який суб'єктивно легше читати. Приклад:

[].forEach((val, index)=>{
   ...
});

Переваги:

  • не включає налаштування змінної (повторюється над кожним елементом масиву)
  • Функції / стрілки-функції охоплюють змінну до блоку
    У наведеному вище прикладі valбуде параметром новоствореної функції. Таким чином, будь-які змінні, викликані valперед циклом, зберігали б свої значення після його закінчення.
  • суб'єктивно більш рентабельний, оскільки може бути простіше визначити, що робить код - він перебирається на безліч; тоді як цикл for-циклу може використовуватися для будь-якої кількості циклів циклу

Продуктивність

Виступ - це хитра тема, яка, як правило, вимагає певного досвіду, коли йдеться про продуманість чи підхід. Для того, щоб заздалегідь визначити (під час розробки), яка оптимізація може знадобитися, програміст повинен мати гарне уявлення про досвід минулого з проблемою, а також добре розуміти потенційні рішення.

Використання jQuery в деяких випадках часом може бути занадто повільним (досвідчений розробник може це знати), тоді як інший час може бути проблемою, в іншому випадку відповідність перехресного браузера бібліотеці та простота виконання інших функцій (наприклад, AJAX, обробка подій) вартує економії часу на розробку (та обслуговування).

Інший приклад - якби продуктивність та оптимізація були все, не було б іншого коду, крім машини чи збірки. Очевидно, що це не так, оскільки існує багато різних мов високого та низького рівнів, кожен з яких має свої компроміси. Ці компроміси включають, але не обмежуються ними, спеціалізацію, простоту та швидкість розробки, простоту та швидкість обслуговування, оптимізований код, код без помилок тощо.

Підхід

Якщо ви не дуже добре розумієте, чи потрібно щось оптимізований код, це, як правило, спочатку правильне написання коду. Звідти ви можете перевірити і точно визначити, що потребує більшої уваги, коли цього потрібно.

Зважаючи на це, певні очевидні оптимізації повинні бути частиною загальної практики і не вимагати жодної думки. Наприклад, розглянемо наступний цикл:

for (var i=0; i < arr.length; ++i ){}

Для кожної ітерації циклу JavaScript arr.lengthвитягує операції калькуляції витрат ключа на кожному циклі. Немає причини, чому цього не повинно бути:

for (var i=0, n=arr.length; i < n; ++i){}

Це робить те саме, але витягується лише arr.lengthодин раз, кешуючи змінну та оптимізуючи ваш код.


25
Відмінна, ретельна, невпевнена відповідь, не обмежена жодним моментом часу, впровадженням або тестом на мікро-орієнтир.

1
Ідеально, саме це я шукав і дає набагато більше глибини, ніж могло б відео. Я дуже ціную це, будучи новим, є багато чому навчитися, і це те, що його легко пропустити, просто віддаючи перевагу одному над іншим без будь-якої причини, яка може заважати вам у майбутньому. Велике дякую!
tonyrobbins

2
for-loop часто мають перевагу з точки зору налагодження: вони тривіла наступати, переривати і перевіряти. За допомогою ForEach () додатковий рівень зворотного виклику може дещо ускладнити речі.
Ерік Ґрандж

1
@FelipeBuccioni спасибі, я насправді збирався вивчити це, оскільки я думаю, що двигуни зараз перевіряють, чи не буде мутований масив, щоб визначити, чи зберігається довжина в кешованому режимі. Хоча, для попередніх цілей, я думаю, що двигуни оптимізації були не такими щедрими, і тривалість була важливою для кожної ітерації. Я перегляну вашу статтю і включу її у відповідь, коли
встигну

6
Мені дуже подобається пояснення в цій відповіді та фразі [...], if performance and optimization was everything, there would be no other code than machine or assembly.. Я вважаю, що за letтвердженням про декларування блокової області локальної змінної, друга перевага forEachбільше не є перевагою перед forциклом, якщо тільки в середовищі без підтримки для let.
користувач7393973
Використовуючи наш веб-сайт, ви визнаєте, що прочитали та зрозуміли наші Політику щодо файлів cookie та Політику конфіденційності.
Licensed under cc by-sa 3.0 with attribution required.