解説
並べ替えたら元の配列まで変わった?sortとtoSortedの違いを試そう
JavaScriptのsortは元の配列を変更し、toSortedは新しい配列を返す。数字の並び方と、constでも中身が変わる理由を小さな作例で確認しよう。

一覧の表示順だけを変えたかったのに、元のデータまで並び替わってしまった。JavaScriptのsort()は、呼び出した配列そのものを変更するよ。元を残すなら、別の配列を作る方法を選ぼう。
このページの目標は「元を変える並べ替え」と「元を残す並べ替え」を区別すること。配列は、複数の値を順番付きで持つ入れ物。記事下の作例はブラウザだけで試せて、保存も送信もしないよ。
sort()は元の配列を並べ替える
const numbers = [20, 3, 100, 1];
const result = numbers.sort((a, b) => a - b);
console.log(numbers); // [1, 3, 20, 100]
console.log(result === numbers); // true
numbersとresultは、並び替え済みの同じ配列を参照している。参照は、ここでは「どの入れ物を指しているか」という意味だよ。返り値を新しい変数へ入れても、それだけで別の入れ物になるわけではない。
(a, b) => a - bは、二つの値の差で順番を決める比較関数。今回は通常の有限な数だけを使って、小さい順に並べている。文字列や欠損値が混ざった入力を、そのまま同じ前提で扱わないようにしよう。
数字でも、比較関数を省略すると期待と違うことがある
const numbers = [20, 3, 100, 1];
numbers.sort();
console.log(numbers); // [1, 100, 20, 3]
比較関数を省略したsort()は、値を文字列に変換した並び方で比較する。「100」は「20」より先に来るので、数の大小順にはならないんだ。
ここで出力される各要素が、文字列へ置き換わったわけではない。比較の仕方と、保存されている値の型は別だよ。今回の配列の中身は数のまま。
元を残すならtoSorted()を選ぶ
const numbers = [20, 3, 100, 1];
const result = numbers.toSorted((a, b) => a - b);
console.log(numbers); // [20, 3, 100, 1]
console.log(result); // [1, 3, 20, 100]
console.log(result === numbers); // false
toSorted()は、並べ替えた新しい配列を返す。元のnumbersは変わらない。作例では、この「元の配列」と「返り値」を並べて表示するよ。
ただし、配列の要素がオブジェクトなら、その中身まで独立した複製を作るものではない。今回は数だけの配列に絞り、配列の並び順が変わるかを比べよう。
作例を三つの方法で比べよう
- 「比較関数なしのsort」を選んで「並べ替える」を押す。元の配列と返り値が、どちらも[1,100,20,3]になる。
- 「数の小さい順のsort」を選んで実行する。両方が[1,3,20,100]になる。
- 「数の小さい順のtoSorted」を選んで実行する。元は[20,3,100,1]、返り値だけが[1,3,20,100]になる。
- 「最初から試す」で未実行の状態へ戻す。
各実行は、同じ初期値から始める作りだよ。前の並べ替え結果を次へ持ち越さないため、方法ごとの違いを比較できる。
constなのに、なぜ中身が変わるの?
constは、その変数へ別の値を再代入することを禁止する宣言。指している配列の中身を一切変更できなくする指定ではない。sort()が動くことと、constの規則は矛盾しないよ。
この違いはletとconstの基礎でも扱っている。コピーを作ったつもりなら「変数名が違うか」だけでなく、どの操作で新しい配列を作ったかを確認しよう。
toSortedが使えないとき
古い実行環境などでtoSortedがない場合、作例は未対応と表示し、その方法の実行を止める。代わりの小さな例は、[...numbers].sort((a, b) => a - b)。先に配列を浅くコピーしてから、そのコピーを並べ替える方法だよ。
編集部ではChromiumで三つの結果と元配列の変化、リセットを確認し、Node.jsでも例の配列を検証した。文字列、NaN、オブジェクトなどを混ぜた場合まで同じ比較規則で済む、という検証ではないよ。
動かしてみよう:並べ替えた後の元配列と返り値
三つの方法を選んで実行し、元の並びと返り値を比べよう。最初から試すと未実行へ戻るよ。

みんなのコメント 0
感想や、試してみたことを聞かせてね。コメント・返信は承認後に公開されます。
最初のコメントをどうぞ。