Posted at

JavaScript で配列の shallow copy をする better な方法


動機

タイトルのとおり、JavaScript で配列のコピーをする必要がありました。

Qiita などで幾つかの方法が紹介されていましたが、

「じゃぁ、どれが一番適切なの?」という疑問が湧き、

その疑問を解決するべく調べた結果を報告します。


結論

結論を先に述べると、 執筆時点では Array.slice() を用いる方法が一番高速でした。

5種類の shallow copy のアルゴリズムと、処理速度比較結果を表示するサイト

https://jsperf.com/duplicate-array-slice-vs-concat/31 

での実行結果を以下に示します。


実行結果

動作環境

- CPU: Intel Core i7-2770K 3.50GHz

- Mem: 32GB

- OS: Windows 10 (64bit)

評価方法

- Browser は Google Chrome, Firefox, MS Edge の3種類を使用

- 5回の試行で評価(実行タイミングを公平にするため、各ブラウザ1回ずつの試行を1セットとして5セットを実施)

(1) Google Chrome 74.0.3729

アルゴリズム
実行速度[Ops/sec]
標準偏差
備考

while [] preallocate
1337.8
89.5

Array.slice
1889.4
124.2
最速!

while push
197.4
20.5
worst

while []
418.2
19.5

Array.concat
1348.8
64.9

(2) Firefox 66.0.0

アルゴリズム
実行速度[Ops/sec]
標準偏差
備考

while [] preallocate
603.6
21.7

Array.slice
1344.4
110.0
最速!

while push
650.4
39.7

while []
608.8
40.8

Array.concat
500.6
27.5
worst

(3) Microsoft Edge 17.17134.0

アルゴリズム
実行速度[Ops/sec]
標準偏差
備考

while [] preallocate
979.8
24.1

Array.slice
1442.4
12.4
最速!

while push
182.8
13.6
worst

while []
425.0
35.4

Array.concat
651.4
59.4


感想


  • 各ブラウザで、処理系の特徴があって面白いなぁと感じました。

  • Edge の Array.slice の処理速度が安定しているのが、ちょっと不思議に感じました(単なる偶然?)。
    これはこれで良い特徴だと思うのですが、今後 Chrome ベースになってしまうのが少し残念?です(競争相手が減るという意味で)。

  • 今回の疑問解決において、上記サイトを見つけることができて、とても幸運でした。先人の労力に感謝!!!