組合せ表を作る 1.すべての組合せを考える

詳細は割愛するが、仕事で3つの装置の部品を組み合わせて何某か評価することとなった。評価するための組合せ表が必要となったので、作ってみた。
エッセンスのみ、一部だけ表すと、こんな感じだ。

これをマクロで作成するなら、例えばこんな感じだろうか。

Sub Sample()
    Dim i As Long
    Dim j As Long
    Dim k As Long
    Dim l As Long
    Dim arr(0 To 3 ^ 4, 1 To 5)
    Dim counter As Long
    
        ' ラベル行データ作成。
        arr(0, 1) = "No."
        arr(0, 2) = "部品1"
        arr(0, 3) = "部品2"
        arr(0, 4) = "部品3"
        arr(0, 5) = "部品4"
        
        ' ボディ部のデータ作成。
        ' "A"が、Chr関数でChr(65)であることを利用している。
        For i = 1 To 3
            For j = 1 To 3
                For k = 1 To 3
                    For l = 1 To 3
                        counter = counter + 1
                        arr(counter, 1) = counter
                        arr(counter, 2) = Chr(i + 64)
                        arr(counter, 3) = Chr(j + 64)
                        arr(counter, 4) = Chr(k + 64)
                        arr(counter, 5) = Chr(l + 64)
        Next l, k, j, i
        
        ' 値貼り付け。
        Range("A1").Resize(3 ^ 4 + 1, 5) = arr
End Sub

今回の例でいえば、部品数が4つなので、4重ループとなっている。
しかしこの数がもっと増えた場合は、マクロを組むのも面倒くさい。

そこで、関数で対応することを考えてみた。
※言うまでもないことだが恐らく、既に広く知られている手法と思う。

まず表に一列追加して、通し番号を三進数に変換する(BASE関数を利用)。

部品数が4つあるので、4桁にしたい。そこでさらに、数字に変えて4桁表示にしよう。

次に、部品のセルに、三進数の各桁の数字を表示してみる。2列目が1文字目、
3列目が2文字目・・・という規則性があるので、A~Cを表示するセルの式は
全て共通で対応できる。

こうすると、0~2が順番に登場する組合せ表が出来上がるわけだ。数字は

  1. 0 ⇒ A
  2. 1 ⇒ B
  3. 2 ⇒ C

に対応している。Char関数で変換しよう。

結果として無事、組合せ表を作成することができた。
登場した数式は、作業用に三進数で表した列と、A~Cを表示する列の2つのみ。式の数という意味では、かなりシンプルになったと思う。

ただし万人受けするかといえば、疑問符が付く(個人的には結構好きかも)。
ということで、もし採用される場合は、時と場合と各位のお好みで。

参考まで。