アルゴリズム ・ Chapter 21

【ハッシュテーブル】

記事 ・ 冒頭を無料公開中

これまで配列を使ってきましたが、配列は探すのが遅いです。この弱点を解決する道具が、ハッシュテーブルです。この講座で一番の山場です。

配列の弱点

会員リストから「佐藤さんの年齢」を調べたいとします。配列だと以下の通り。

const users = [
  { name: "田中", age: 28 },
  { name: "鈴木", age: 17 },
  { name: "佐藤", age: 35 },
];
const sato = users.find((u) => u.name === "佐藤");

findは先頭から順に確認します。3人なら一瞬ですが、100万人なら最悪100万回、つまりO(n)です。1回ならまだしも、「1000人分の名前について順に調べる」となると、100万×1000回の確認になり、現実的な時間で終わりません。

これは、探すたびに全員を見るのが問題なのです。欲しいのは、名前を言えば一発でデータが出てくる仕組み、つまり辞書です。

キーで引く、オブジェクトは辞書である

実は、その道具はすでに手元にあります。オブジェクトです。

ages["佐藤"] は、全員を順に確認しません。キー(名前)から保存場所を直接割り出して、そこを読むだけ。データが100万人分あってもO(1)です。なぜそんなことが可能なのか、その内部の仕組み(ハッシュ関数)はこの教材の後半「作る編」で種明かしします。

この「キー→値を1回で引ける構造」の一般名がハッシュテーブルです。言語によって連想配列、辞書、マップとも呼ばれます。JavaScriptではオブジェクトがその役割を果たし、型は Record<キーの型, 値の型> と書きます(スタック演習の括弧の対応表 Record<string, string> が、実はハッシュテーブルの初登場でした)。

定番パターン① 数える(頻度カウント)

ハッシュテーブルの一番使われるのは「数える」仕事です。文章に各単語が何回出てくるか、数えてみます。

核心は (counts[word] ?? 0) + 1 の1行です。?? は「左がundefinedなら、右を使う」という演算子(Null合体演算子)です。初めて見る単語なら「0回」から数え始め、既にあればその値に1を足す。この頻度カウントの型は、コーディングテストで最頻出のパターンです。「一番多く登場する文字は?」「重複はあるか?」「アナグラムか?」という数え上げ系の問題は、ほぼすべてこの3行から始まります。

定番パターン② 「あるかどうか」だけならSet

値は要らず、「存在するかどうか」だけ知りたい場面には、専用の道具があります。Set(セット)です。重複なしの値の集まりです。

このチャプターの続きは受講生限定です

本文の残り、図解・実行できるコードブロック・演習はプラン加入後に読めます。

料金プランを見る