2
2

Delete article

Deleted articles cannot be recovered.

Draft of this article would be also deleted.

Are you sure you want to delete this article?

WeakMapとWeakSetの記憶と消滅:JavaScriptのガーベジコレクションとメモリ安全な設計戦略

Posted at

概要

JavaScriptではメモリの管理が自動的に行われるが、“保持しすぎること”によるメモリリークのリスクは開発者側にある。
この課題に対し、WeakMap および WeakSet弱参照という概念で解決を提供する。

  • Map / Set は値を「保持」する
  • WeakMap / WeakSet は値を「参照」する

本稿では、この特性を活かした設計例と、メモリリーク回避・隠蔽状態管理・キャッシュ設計への応用方法を示す。


1. WeakMapとは何か?

const wm = new WeakMap();
const obj = { name: 'Toto' };

wm.set(obj, 'secret');
console.log(wm.get(obj)); // 'secret'
  • キーはオブジェクト限定
  • 弱参照obj がGCで消えれば、wm のデータも自動削除
  • ❌ キー列挙・サイズ取得は不可能(wm.keys().size は存在しない)

2. WeakSetとは何か?

const ws = new WeakSet();
const o = { id: 1 };

ws.add(o);
console.log(ws.has(o)); // true
  • オブジェクトのみ格納可
  • ✅ 同様にGCで自動解放される

なぜ「弱参照」なのか?

通常の Map:
  キー = 強参照 → GCの対象にならない

WeakMap:
  キー = 弱参照 → オブジェクトがどこからも参照されなければGCされる

→ ✅ “知らないうちにリーク”を防ぐ仕組み


使用ユースケース①:プライベートデータの隠蔽

const privateData = new WeakMap();

class User {
  constructor(name) {
    privateData.set(this, { name });
  }

  getName() {
    return privateData.get(this).name;
  }
}

const u = new User('Toto');
u.getName(); // 'Toto'
  • ✅ 外部からアクセス不能
  • ✅ ユーザーが削除されれば、プライベートデータも自動消滅

使用ユースケース②:DOMノードへのメタ情報紐付け(メモリセーフ)

const cache = new WeakMap();

function bindMeta(domNode, meta) {
  cache.set(domNode, meta);
}

function getMeta(domNode) {
  return cache.get(domNode);
}

→ ✅ DOMが削除されたら、cacheも自動解放 → メモリリークを回避


使用ユースケース③:内部キャッシュ(GC安全なメモ)

const results = new WeakMap();

function heavyCalc(input) {
  if (results.has(input)) return results.get(input);

  const output = /* ... heavy computation ... */;
  results.set(input, output);
  return output;
}

→ ✅ キャッシュは存在する限り利用され、不要になれば解放される


制約と注意点

特性 WeakMap / WeakSet
キー/値はオブジェクトのみ ✅(プリミティブ不可)
キー列挙 ❌ 不可(セキュリティ/GCのため)
サイズ取得 ❌ 不可
メモリ管理 ✅ 自動GCで安全

設計判断フロー

① 状態を“外から見せたくない”? → WeakMap に格納

② DOMや一時的なオブジェクトに紐づく情報を持ちたい? → WeakMap を使う

③ GCとともに自動的にデータを破棄したい? → WeakMap/WeakSet を選択

④ プリミティブなキーを使いたい? → Map を使う(WeakMapでは不可)

⑤ データ一覧が必要? → Map / Set を選択(Weak系では不可)

よくある誤解

❌ WeakMapは“弱いセキュリティ”を提供する?

→ ❌ 違います。セキュリティ目的ではなく、メモリ安全のため


❌ WeakMapに入れたら明示的に削除できない?

→ ✅ .delete(key) は可能。ただし不要な場合はGCに任せてよい


結語

WeakMap / WeakSet は、データを「保持する」のではなく、「忘れることを許す」構造である。

  • オブジェクトのライフサイクルに寄り添い、
  • メモリリークを構造的に防ぎ、
  • 外部から不可視な状態を安全に設計できる

“見えない記憶、忘れられる設計”。それが Weak な構造の本質である。

2
2
0

Register as a new user and use Qiita more conveniently

  1. You get articles that match your needs
  2. You can efficiently read back useful information
  3. You can use dark theme
What you can do with signing up
2
2

Delete article

Deleted articles cannot be recovered.

Draft of this article would be also deleted.

Are you sure you want to delete this article?