Слід використовувати техніку на основі циклу. Інші відповіді на цій сторінці, що базуються на використанні, .apply
не можуть мати великі масиви.
Досить короткою реалізацією циклу є:
Array.prototype.extend = function (other_array) {
/* You should include a test to check whether other_array really is an array */
other_array.forEach(function(v) {this.push(v)}, this);
}
Потім ви можете зробити наступне:
var a = [1,2,3];
var b = [5,4,3];
a.extend(b);
Відповідь DzinX (за допомогою push.apply) та інших .apply
заснованих методів не вдається, коли масив, який ми додаємо, великий (тести показують, що для мене великим є> 150 000 записів приблизно в Chrome і> 500 000 записів у Firefox). Ви можете бачити цю помилку в цьому jsperf .
Помилка виникає через те, що розмір стека викликів перевищений, коли "Function.prototype.apply" викликається великим масивом як другим аргументом. (У MDN є примітка про небезпеку перевищення розміру стека виклику за допомогою Function.prototype.apply - див. Розділ під назвою "застосувати та вбудовані функції".)
Для порівняння швидкості з іншими відповідями на цій сторінці ознайомтеся з цим jsperf (завдяки EaterOfCode). Реалізація на основі циклу за швидкістю схожа на використання Array.push.apply
, але, як правило, трохи повільніше, ніж Array.slice.apply
.
Цікаво, що якщо масив, який ви додаєте, є рідким, forEach
заснований вище метод може скористатися обмеженістю та перевершити .apply
основані методи; перевірити цей jsperf, якщо ви хочете перевірити це на собі.
До речі, не спокушайтесь (як я!) Ще більше скоротити реалізацію forEach до:
Array.prototype.extend = function (array) {
array.forEach(this.push, this);
}
тому що це дає результати сміття! Чому? Оскільки Array.prototype.forEach
надано три аргументи функції, яку вона викликає - це: (element_value, element_index, source_array). Все це буде висунуто на ваш перший масив для кожної ітерації, forEach
якщо ви використовуєте "forEach (this.push, this)"!
a.push(...b)
. Це за концепцією схоже на головну відповідь, але оновлено для ES6.