개념
크기가 각각 b와 a인 서로 다른 두 수열 arr1[b]와 arr2[a]가 주어졌을 때, 이 두 수열을 하나로 합친 전체 데이터의 평균(mean)과 분산(variance)을 구하는 것이 이 글의 목표입니다.
입력
Arr1[] = { 24, 46, 35, 79, 13, 77, 35 };
Arr2[] = { 66, 68, 35, 24, 46 };출력
Mean1: 44.1429 Mean2: 47.8 StandardDeviation1: 548.694 StandardDeviation2: 294.56 Combined Mean: 45.6667 d1 square: 2.322 d2_square: 4.5511 Combined Variance: 446.056
풀이 방법
먼저 계산에 사용할 기호를 다음과 같이 정의합니다.
- n1 : 첫 번째 그룹(영역 1)의 관측값 개수
- n2 : 두 번째 그룹(영역 2)의 관측값 개수
- X1 : 영역 1의 평균
- X2 : 영역 2의 평균
- S1 : 영역 1의 표준편차
- S2 : 영역 2의 표준편차
- S12 : 영역 1의 분산
- S22 : 영역 2의 분산
전체 그룹의 평균을 X라고 할 때, 각 그룹의 평균과 전체 평균 사이의 차이는 다음과 같습니다.
d1 = X − X1
d2 = X − X2
전체 그룹의 평균 X는 관측값 개수를 가중치로 하는 가중 평균 방식으로 계산합니다.
X = (n1 × X1 + n2 × X2) / (n1 + n2)
전체 그룹의 분산은 다음 공식으로 구합니다.
분산 = [n1 × (S12 + d12) + n2 × (S22 + d22)] / (n1 + n2)
즉, 각 그룹의 분산에 "그룹 평균과 전체 평균 사이 거리의 제곱(d²)"을 더한 뒤, 관측값 개수로 가중 평균을 내는 방식입니다.
C++ 구현 예제
// C++ 프로그램: 두 수열의 결합 평균과 분산 구하기
#include <bits/stdc++.h>
using namespace std;
// 수열의 평균을 구하는 함수
float mean(int Arr[], int b){
int sum1 = 0;
for (int i = 0; i < b; i++)
sum1 = sum1 + Arr[i];
float mean = (float)sum1 / b;
return mean;
}
// 수열의 표준편차를 구하는 함수
float sd(int Arr[], int b){
float sum1 = 0;
for (int i = 0; i < b; i++)
sum1 = sum1 + (Arr[i] - mean(Arr, b)) *
(Arr[i] - mean(Arr, b));
float sdd = sum1 / b;
return sdd;
}
// 서로 다른 두 수열의 결합 분산을 구하는 함수
float combinedVariance(int Arr1[], int Arr2[], int b, int a){
// mean1, mean2 : 두 배열의 평균
float mean1 = mean(Arr1, b);
float mean2 = mean(Arr2, a);
cout << "Mean1: " << mean1
<< " mean2: " << mean2 << endl;
// sd1, sd2 : 두 배열의 표준편차
float sd1 = sd(Arr1, b);
float sd2 = sd(Arr2, a);
cout << "StandardDeviation1: " << sd1
<< " StandardDeviation2: " << sd2
<< endl;
// combinedMean : 두 배열의 결합 평균
float combinedMean = (float)(b * mean1 + a * mean2) / (b + a);
cout << "Combined Mean: " << combinedMean
<< endl;
// d1_square, d2_square : 결합 평균에 대한 편차의 제곱
float d1_square = (mean1 - combinedMean) * (mean1 - combinedMean);
float d2_square = (mean2 - combinedMean) * (mean2 - combinedMean);
cout << "d1 square: " << d1_square
<< " d2_square: " << d2_square
<< endl;
// combinedVar : 두 배열의 결합 분산
float combinedVar = (b * (sd1 + d1_square) + a * (sd2 + d2_square)) / (b + a);
cout << "Combined Variance: " << combinedVar;
}
// 드라이버 함수
int main(){
int Arr1[] = { 24, 46, 35, 79, 13, 77, 35 };
int Arr2[] = { 66, 68, 35, 24, 46 };
int b = sizeof(Arr1) / sizeof(Arr1[0]);
int a = sizeof(Arr2) / sizeof(Arr2[0]);
// 결합 평균·분산 계산 함수 호출
combinedVariance(Arr1, Arr2, b, a);
return 0;
}실행 결과
Mean1: 44.1429 mean2: 47.8 StandardDeviation1: 548.694 StandardDeviation2: 294.56 Combined Mean: 45.6667 d1 square: 2.322 d2_square: 4.5511 Combined Variance: 446.056
참고 사항
위 구현에서 sd() 함수는 "편차 제곱의 합 ÷ n"을 반환하므로, 출력에서 StandardDeviation으로 표시된 값(548.694, 294.56)은 실제로는 각 그룹의 분산에 해당합니다. 이 값들이 결합 분산 공식의 S12, S22 자리에 그대로 사용되므로 최종 결과에는 문제가 없습니다.