VBAで重複を数えるならDictionaryが便利 ― 参照設定なしで安全に集計する

VBA・Officeカテゴリを表すパンダのイラスト VBA・Office

この記事について
この記事は、生成AIを活用した自動生成フローで作成しています。Microsoft LearnのDictionary object仕様を確認し、既存サンプルも再レビューして、入力シートの列を消さない構成へ修正しています。

検証ステータス:📘 公式仕様確認済み・サンプル安全性レビュー済み・Excel実機確認は未実施

VBAで重複を数えるならDictionaryが便利 ― 参照設定なしで安全に集計する

Excel VBAで「同じ値が何件あるか」を1回の走査で集計するなら、Scripting.Dictionary が便利です。CreateObject("Scripting.Dictionary") を使えば、VBEの参照設定を追加しないLate Bindingでも利用できます。

今回はもう1点、結果の出し方も重要です。入力シートの空いていそうな列を丸ごと消して結果を書くのではなく、専用の結果シートへ出します。

Dictionaryの考え方

Dictionaryは「キー」と「値」の組み合わせを持ちます。今回はセルの文字列をキー、出現件数を値にします。

東京 -> 3
大阪 -> 2
福岡 -> 1

同じキーが来たら件数を1増やし、初めてなら1で追加します。

Set dict = CreateObject("Scripting.Dictionary")

' 大文字小文字を同じキーとして扱います。
' キーを追加する前にCompareModeを設定します。
dict.CompareMode = vbTextCompare

For row = 2 To lastRow
    key = Trim$(CStr(sourceWs.Cells(row, "A").Value2))

    If Len(key) > 0 Then
        If dict.Exists(key) Then
            dict(key) = CLng(dict(key)) + 1
        Else
            dict.Add key, 1
        End If
    End If
Next row

Late Bindingにする理由

Early Bindingなら Scripting.Dictionary 型を直接宣言できますが、通常は「Microsoft Scripting Runtime」への参照設定が必要です。Late Bindingでは ObjectCreateObject を使うため、配布先で参照設定が外れて動かなくなる問題を減らせます。

一方、VBEの入力補完や型チェックは弱くなります。教材や社内配布では「参照設定を不要にしたいか」「開発時の型支援を優先したいか」で選びます。

出力先を専用シートにする

最初の版では入力シートの C:D 列を ClearContents していました。しかし、そこに利用者の別データがあれば消えてしまいます。

そこで現在版は 重複集計結果 シートを作り、そのシートだけを再利用します。

flowchart LR
    A[入力シート A列] --> B[Scripting.Dictionary]
    B --> C[キーごとに件数を加算]
    C --> D[重複集計結果シート]
    D --> E[値 / 件数]

「動くコード」でも、既存データをどう扱うかまで見ないと実務向けにはなりません。今回の夜間生成では、記事化の前にサンプル側も直しています。

このサンプルの判定ルール

  • A2以降を対象にする

  • 前後の空白は Trim$ で除く

  • 空文字は数えない

  • vbTextCompare なので英字の大文字小文字は区別しない

  • 値は CStr で文字列化してキーにする

たとえば数値の 123 と文字列の "123" を厳密に別物として数えたい用途には、そのままでは向きません。データ型まで区別したい場合はキーの作り方を変えます。

GitHubサンプル

公式情報・一次情報

ライセンス:本記事のテキスト/コードは特記なき限り CC BY 4.0 です。引用の際は出典URL(本ページ)を明記してください。
利用ポリシー もご参照ください。
タイトルとURLをコピーしました