VBAの配列を覚えよう

VBAプログラミング

静的配列

配列というのは、簡単に言えば複数の情報を一つの変数に入れたものです。下記のような形となります。

Sub test()

    Dim Dogs(2) As String
    
    Dogs(0) = "柴犬"
    Dogs(1) = "秋田犬"
    Dogs(2) = "チワワ"
    
    Debug.Print (Dogs(0))

End Sub

こちらを実行すると、Dogs(0)に格納した”柴犬”という文字列がイミディエイトウィンドに出力されます。

なお、配列の()内の番号をインデックスと呼び、必ず0から始まります。また、配列に代入している値を要素と呼びます。

動的配列

上記の場合、配列に3つの値が入るという前提で行っていますが、もしこの数が増える場合、下記のように、配列にデータを追加するたびに、Redimという書き方で、配列を再定義してあげる必要があります。

Sub test()

    Dim Dogs() As String
    
    ReDim Dogs(2)
    
    Dogs(0) = "柴犬"
    Dogs(1) = "秋田犬"
    Dogs(2) = "チワワ"
    
    Debug.Print (Dogs(0))

    ReDim Dogs(3)

    Dogs(3) = "トイプードル"

End Sub

2次元配列

例えば上記の例で、各犬種ごとに名前があり、その名前も保持したいとします。

その場合、2次元配列を使用すれば保持することができます。

例えば下記のようなデータの場合。

犬種名前
柴犬シバクン
秋田犬アキチャン
チワワチワジロウ
Sub test()
    
    Dim Dogs(2, 1) As String
    
    Dogs(0, 0) = "柴犬"
    Dogs(1, 0) = "秋田犬"
    Dogs(2, 0) = "チワワ"

    Dogs(0, 1) = "シバクン"
    Dogs(1, 1) = "アキチャン"
    Dogs(2, 1) = "チワジロウ"

    Debug.Print (Dogs(0, 1))

End Sub

このようにして、表の情報を配列に代入していくことができます。

最初に定義しているDogs(2, 1)の箇所は、インデックスの2が、表の行数、その隣の1が、列数だと思ってください。

インデックスは0から始まりますので、実際は行数が3、列数が2となります。

ただ、2次元配列は、上記のように要素を数字で表していますので、少し分かりにくいですね。

また、データの件数が決まっていたら、上記のようにDogs(2, 1)として、行数を指定出来ますが、行数が固定出ない場合は、またRedimを使用して、行数を指定して定義してあげる必要があります。

何か便利は配列はないかな?。Redimとか使わないやつ。

それではディクショナリ(連想配列)について説明します。

ディクショナリ(連想配列)

ディクショナリは、簡単に言えば、インデックスを数値ではなくて、データそのものをインデックスとすることができます。

ただし、下記の条件のときのみ使用できます。

  • キー情報がある
  • 保持できる列は1つのみ

例えば下記のようなデータの場合。

顧客コード顧客名住所
C001柴犬株式会社東京都XXX
C002秋田犬合同会社神奈川県XXX
C003チワワ株式会社大阪府XXX

よくあるタイプの顧客マスタですね。顧客コードはキーとなっていて、必ず1行ごとにコードが降られていて、重複はしないものとします。

この場合、顧客コードそのものをインデックスとして扱います。

ちなみにディクショナリの場合、インデックスではなく、キーと呼び、代入される値はアイテムと呼ばれます。

コードは下記のようになります。(保持できる列は1つだけですので、住所は無視しています)

Sub test()
    
    Dim Customers As Object
    Set Customers = CreateObject("Scripting.Dictionary")

    Customers.Add "C001", "柴犬株式会社"
    Customers.Add "C002", "秋田県合同会社"
    Customers.Add "C003", "チワワ株式会社"

    Debug.Print (Customers("C002"))

End Sub

こちらを実行すると、”秋田県合同会社”が出力されます。

Customersというオブジェクトがディクショナリとして設定されています。

その後、Customers.Add Key, Item という構文で、ディクショナリにデータを追加しています。

まず2次元配列と比較して便利なのが、データを増やしたい場合、Redimは不要で、上記の場合

Customers.Add “C003”, “チワワ株式会社”
の下に
Customers.Add ‘C004″, “プードル株式会社” 

というように追加ができます。
※ただし、Keyの箇所は重複してはいけません。

また、データを取り出したいときも、Customers(“C002”)だけで、それに紐づいたItemの “秋田県合同会社” を取得できますので、とても分かりやすいです。

もしこれを2次元配列で表すと、下記のようになります。
配列に入れたデータをループして、C002に紐づいた会社名を出力しています。

Sub test()
    
 Dim Dogs(2, 1) As String
    
    Dogs(0, 0) = "C001"
    Dogs(1, 0) = "C002"
    Dogs(2, 0) = "C003"

    Dogs(0, 1) = "柴犬株式会社"
    Dogs(1, 1) = "秋田犬合同会社"
    Dogs(2, 1) = "チワワ株式会社"

    '行数分ループ
    For i = 0 To 2
        '1列目がC0002の場合、その行の2列目を出力
        If Dogs(i, 0) = "C002" Then
            Debug.Print (Dogs(1, 1))
        End If
    Next

End Sub

このような場合、明らかにディクショナリの方が分かりやすくコードを書くことができますね。

複数行で複数の列を保持したい場合はどうすればいいですか?

ディクショナリを必要な列分作るとか、2次元配列でゴリ押しするとか、クラスを使うとかいろいろあります。

複数行、複数列を丸ごと保持したいということであれば、一つの方法として、クラスを使用することが出来ますが、コードのボリュームが増えてしまいますので、まずはシンプルに出来ないか検討してみるのがよいかもしれません。

クラスについては下記リンクをご参考下さい。

コメント

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