【実務・中級編】【中級】テーブル内の不要なインデックスをVBAで検出し、書き込み速度を改善する – Access VBA解析バイブル

スポンサーリンク

【Access極限最適化】不要インデックスを撲滅せよ:VBAによるパフォーマンスチューニングの真髄

「Accessが重い」「新規レコードの保存に時間がかかる」。
現場からそんな悲鳴が上がったとき、多くの初心者はフォームのクエリを疑う。だが、熟練のアーキテクトが真っ先にメスを入れるのは、「肥大化したインデックス」だ。

インデックスは検索速度を劇的に向上させる魔法だが、書き込み(INSERT/UPDATE)においては毒となる。B-Tree構造を維持するために、レコードを追加するたびにAccessは全インデックスを再構築するからだ。

今回は、使われていない(あるいは過剰な)インデックスをVBAで検出し、データベースのポテンシャルを解放する「外科手術」の作法を伝授する。

—

1. なぜ「インデックス」がボトルネックになるのか

インデックスは、データが挿入されるたびに「並び替え」と「平衡化」のコストを要求する。

  • プライマリキー(PK): 必須。
  • 外部キー(FK): リレーションシップの整合性維持に必須だが、過剰な場合は再考が必要。
  • 検索用インデックス: これが曲者だ。過去の要件で作成されたまま、現在のクエリでは一切使われていないインデックスが、書き込み速度を削り続けている。

2. インデックス診断の論理設計

DAO(Data Access Objects)を使えば、テーブルのメタデータをプログラムから操作できる。`TableDef` オブジェクトから `Indexes` コレクションを走査し、システムインデックス(プライマリキー等)を除外した「ユーザー定義インデックス」を抽出するのが戦略だ。

以下のコードは、「どのテーブルに、どのフィールドでインデックスが張られているか」をイミディエイトウィンドウに出力する診断ツールである。

‘ ———————————————————————-
‘ プロシージャ名: DiagnoseTableIndexes
‘ 概要: データベース内の全テーブルからインデックス構成を一覧化する
‘ ———————————————————————-
Public Sub DiagnoseTableIndexes()
Dim db As DAO.Database
Dim tdf As DAO.TableDef
Dim idx As DAO.Index
Dim fld As DAO.Field

Set db = CurrentDb

Debug.Print “— インデックス診断レポート —”

For Each tdf In db.TableDefs
‘ システムテーブル(MSys…)は除外
If Left(tdf.Name, 4) <> “MSys” Then
For Each idx In tdf.Indexes
‘ プライマリキーは除外して診断対象とする
If Not idx.Primary Then
Debug.Print “Table: ” & tdf.Name & ” | Index: ” & idx.Name
For Each fld In idx.Fields
Debug.Print vbTab & “Field: ” & fld.Name
Next fld
End If
Next idx
End If
Next tdf

Set db = Nothing
MsgBox “診断が完了しました。イミディエイトウィンドウを確認してください。”, vbInformation
End Sub

—

3. 実行時の「落とし穴」と保守性への配慮

このスクリプトを運用する際、以下の3点に注意せよ。これができない者は、本番環境で事故を起こす。

1. 排他制御の徹底:
`TableDef` を操作する際は、ユーザーが他のフォームでそのテーブルを開いているとエラーになる。必ずDAOでデータベースを明示的に開き、適切なエラーハンドリングを実装すること。
2. 削除は慎重に:
コードでインデックスを削除する `tdf.Indexes.Delete “インデックス名”` を実装したくなるだろう。だが、「削除する前に必ずバックアップを取る」こと。そして、そのインデックスが本当に使用されていないか、クエリの実行計画を `EXPLAIN` 的な観点(クエリプランの確認)で精査するプロセスを忘れてはならない。
3. リレーションシップの罠:
「リレーションシップの設定」で作成されたインデックスは、VBAから単純に削除できない場合がある。まずはUI上でリレーションシップを確認し、不要なものを手動で消してから、残った「野良インデックス」をVBAで一掃するのが定石だ。

4. アーキテクトからの提言

パフォーマンス改善の本質は、「足すこと」ではなく「削ること」にある。

多くの開発者は、不安から「とりあえずインデックスを貼る」という逃げの設計を行う。しかし、真のプロは「クエリがインデックスを必要としているか」を証明してから実装する。

まずは上記の診断スクリプトで、あなたのDBの中に眠る「使われないインデックス」の正体を突き止めろ。それが、あなたのシステムを高速化させる第一歩だ。コードは道具に過ぎない。重要なのは、その裏にあるデータの流れを読み解く「視座」であることを忘れないでほしい。

—
次回のトピック:
「DAOの `Recordset` を使いこなし、バルクインサートで書き込み速度を極限まで引き上げる手法」について解説する。期待していてくれ。

タイトルとURLをコピーしました