Мені не відомий універсальний метод генерування корельованих випадкових величин з будь-якими граничними розподілами. Отже, я запропоную спеціальний метод для генерування пар рівномірно розподілених випадкових змінних із заданою кореляцією Пірсона. Не втрачаючи загальності, я вважаю, що бажаний граничний розподіл є стандартним рівномірним (тобто опора дорівнює ).[0,1]
Пропонований підхід спирається на таке:
а) Для стандартних рівномірних випадкових величин і з відповідними функціями розподілу і маємо , при . Таким чином, за визначенням rho Спірмена є
Отже, коефіцієнт кореляції Спірмана та Пірсона рівні (однак версії зразків можуть, однак, відрізнятися).U1U2F1F2Fi(Ui)=Uiρ S ( U 1 , U 2 ) = c o r r ( F 1 ( U 1 ) , F 2 ( U 2 ) ) = c o r r ( U 1 , Ui=1,2
ρS(U1,U2)=corr(F1(U1),F2(U2))=corr(U1,U2).
б) Якщо - випадкові величини з безперервними полями, а копула Гаусса з коефіцієнтом кореляції (Пірсона) , то Спірмена є
Це дозволяє легко генерувати випадкові величини, які мають бажане значення rho Spearman.X1,X2ρ
ρS(X1,X2)=6πarcsin(ρ2).
Підхід полягає у формуванні даних з копули Гаусса з відповідним коефіцієнтом кореляції таким, що rho Spearman відповідає бажаній кореляції для рівномірних випадкових величин.ρ
Алгоритм моделювання
Нехай позначає бажаний рівень кореляції, а кількість пар, які потрібно генерувати. Алгоритм:rn
- Обчисліть .ρ=2sin(rπ/6)
- Створити пару випадкових змінних з копули Гаусса (наприклад, при такому підході )
- Повторіть крок 2 рази.n
Приклад
Наступний код є прикладом реалізації цього алгоритму з використанням R з цільовою кореляцією і пар.r=0.6n=500
## Initialization and parameters
set.seed(123)
r <- 0.6 # Target (Spearman) correlation
n <- 500 # Number of samples
## Functions
gen.gauss.cop <- function(r, n){
rho <- 2 * sin(r * pi/6) # Pearson correlation
P <- toeplitz(c(1, rho)) # Correlation matrix
d <- nrow(P) # Dimension
## Generate sample
U <- pnorm(matrix(rnorm(n*d), ncol = d) %*% chol(P))
return(U)
}
## Data generation and visualization
U <- gen.gauss.cop(r = r, n = n)
pairs(U, diag.panel = function(x){
h <- hist(x, plot = FALSE)
rect(head(h$breaks, -1), 0, tail(h$breaks, -1), h$counts/max(h$counts))})
На малюнку нижче діагональні графіки показують гістограми змінних та , а графіки показують графіки розкиду та .
U1U2U1U2
За кондукцією випадкові величини мають однакові межі та коефіцієнт кореляції (близький до) . Але через ефект вибірки коефіцієнт кореляції модельованих даних не точно дорівнює .rr
cor(U)[1, 2]
# [1] 0.5337697
Зауважте, що gen.gauss.cop
функція повинна працювати з більш ніж двома змінними, просто вказавши більшу кореляційну матрицю.
Модельне дослідження
Наступне дослідження моделювання, повторене для цільової кореляції дозволяє припустити, що розподіл коефіцієнта кореляції збільшиться до потрібної кореляції у міру збільшення розміру вибірки .r=−0.5,0.1,0.6n
## Simulation
set.seed(921)
r <- 0.6 # Target correlation
n <- c(10, 50, 100, 500, 1000, 5000); names(n) <- n # Number of samples
S <- 1000 # Number of simulations
res <- sapply(n,
function(n, r, S){
replicate(S, cor(gen.gauss.cop(r, n))[1, 2])
},
r = r, S = S)
boxplot(res, xlab = "Sample size", ylab = "Correlation")
abline(h = r, col = "red")