JavaScript
 Computer >> コンピューター >  >> プログラミング >> JavaScript

【JavaScript】reduce()メソッドだけで配列を並べ替える方法

本記事では、数値の配列を受け取り、Array.prototype.sort()メソッドを使わずに並べ替えを行うJavaScript関数の実装方法を解説します。条件として、ソート処理にはArray.prototype.reduce()メソッドを使用します。

reduce()だけでソートする考え方

ポイントは、reduce()の累積値(アキュムレータ)を「すでにソート済みの配列」として扱うことです。元の配列から要素を1つずつ取り出し、そのたびにアキュムレータ内の適切な位置へ挿入していけば、最終的に完全にソートされた配列が完成します。これは古典的な挿入ソート(insertion sort)のアルゴリズムを、reduce()とsplice()で表現したものです。

サンプル配列

const arr = [4, 56, 5, 3, 34, 37, 89, 57, 98];

コード例

以下が実際のコードです。

// sort() メソッドを使わずに
// 従来型のループ構文も使わずに
// ES6 の reduce() だけで配列をソートします
const arr = [4, 56, 5, 3, 34, 37, 89, 57, 98];

const sortWithReduce = arr => {
  return arr.reduce((acc, val) => {
    let ind = 0;
    // アキュムレータ内で val より小さい要素の後ろまで位置を進める
    while (ind < acc.length && val > acc[ind]) {
      ind++;
    }
    acc.splice(ind, 0, val);
    return acc;
  }, []);
};

console.log(sortWithReduce(arr));

実行結果

コンソールには次のような出力が表示されます。

[
  3,  4,  5, 34, 37,
 56, 57, 89, 98
]

コードの解説

  • 初期値の空配列 []:reduce()の第2引数に空配列を渡すことで、ソート結果を格納する新しい配列をアキュムレータとして用意しています。
  • while文による位置探索:現在の要素valを挿入すべきインデックスを、アキュムレータの先頭から順に比較しながら求めます。
  • splice()による挿入:求めた位置indにvalを挿入します。これにより、アキュムレータは毎回ソート済みの状態を保ちます。

なお、比較条件を「val > acc[ind]」から「val < acc[ind]」に変更すれば、降順(大きい順)のソートにも簡単に対応できます。このようにreduce()を活用すれば、sort()メソッドやfor文に頼らずとも、関数型的で宣言的なスタイルで配列の並べ替えを実装できます。

  1. JavaScriptの配列findIndex()関数の使い方をわかりやすく解説

    JavaScriptのfindIndex()関数は、配列の中から指定した条件を満たす最初の要素を見つけ、そのインデックス番号を返すメソッドです。条件に合う要素が見つかった場合、その要素のインデックスが返されます。もし条件を満たす要素がひとつも存在しない場合は、-1が返されるという特徴があります。findIndex()の基本的な使い方以下は、findIndex()関数を使ったサンプルコードです。ボタンをクリックすると、配列内の「lion」という要素のインデックスを取得して表示します。サンプルコード<!DOCTYPE html> <html lang="ja"

  2. JavaScriptの配列some()メソッドの使い方をわかりやすく解説

    JavaScriptのArray.some()メソッドは、配列の要素の中に、指定されたテスト(条件)を満たすものが「1つでも存在するかどうか」を判定するためのメソッドです。ここでいうテストとは、配列の各要素に対して順番に実行されるコールバック関数のことを指します。コールバック関数が1つでもtrueを返した時点でsome()はtrueを返し、すべての要素が条件を満たさなかった場合はfalseを返します。なお、空の配列に対して呼び出した場合は常にfalseを返すという仕様になっている点にも注意しましょう。some()メソッドのサンプルコード以下は、配列のsome()メソッドを使った具体的な実装例で