カイ二乗検定はとても使いやすい検定法で、Excelの関数としてもCHISQ.TEST関数が用意されています。実測値と期待値の範囲を引数として渡すのですが、期待値を実測値から計算することが多くあります。また、2×2の分割表の検定を大量に行いたい場合、元のデータが1行ごとになっていても、いちいち分割表の形に変換する必要があります。そこで、VBAで次のようなユーザ定義関数を作成します。
- 期待値の計算をVBAで行うことで、引数として実測値だけ渡せるようにする
- 2×2の分割表の検定については、4つの値を引数として渡せるようにする
次のコードを標準モジュールに貼り付けて利用してください。
Option Explicit
Function ChiSqTest22(v11 As Long, v12 As Long, v21 As Long, v22 As Long) As Double
'2*2分割表の4つの値からカイ二乗検定のP値を返す
Dim mat(1 To 2, 1 To 2) As Long
mat(1, 1) = v11: mat(1, 2) = v12: mat(2, 1) = v21: mat(2, 2) = v22
ChiSqTest22 = ChiSquareTest(mat)
End Function
Function ChiSqTest(rg1 As Range) As Double
'観測値の範囲を受け取り、カイ二乗検定のP値を返す
ChiSqTest = ChiSquareTest(rg1.Value)
End Function
Function ChiSquareTest(observedValues As Variant) As Double
' 観測値の2次元配列を受け取り、カイ二乗検定のP値を返す
Dim numRows As Long
Dim numCols As Long
Dim chiSquareValue As Double
' 行数と列数を取得
numRows = UBound(observedValues, 1)
numCols = UBound(observedValues, 2)
Dim rowSums() As Double
ReDim rowSums(1 To numRows)
Dim colSums() As Double
ReDim colSums(1 To numCols)
Dim totalSum As Double
Dim i As Long, j As Long
'各行、列、全体の合計を取得
For i = 1 To numRows
For j = 1 To numCols
rowSums(i) = rowSums(i) + observedValues(i, j)
colSums(j) = colSums(j) + observedValues(i, j)
totalSum = totalSum + observedValues(i, j)
Next j
Next i
' 期待値を計算
Dim expectedValues() As Variant
ReDim expectedValues(1 To numRows, 1 To numCols)
For i = 1 To numRows
For j = 1 To numCols
expectedValues(i, j) = (rowSums(i) * colSums(j)) / totalSum
Next j
Next i
' P値を計算して戻り値として返す
ChiSquareTest = Application.WorksheetFunction.ChiSq_Test(observedValues, expectedValues)
End Function