我可以生成一个二进制变量y
,如下所示:
clear
set more off
gen y =.
replace y = rbinomial(1, .5)
如何生成与n
相关的y_1, y_2, ..., y_n
变量rho
?
答案 0 :(得分:2)
Correlation是成对的度量,因此我假设当您谈论二进制(Bernoulli)值Y 1 ,...,Y n 具有相关性时的rho
中,您将它们视为时间序列Y i :i = 1,...,n,具有共同均值p
的伯努利值,方差{ {1}}和p*(1-p)
的滞后1相关性。
我能够使用相关性和条件概率的定义来计算。鉴于这是一堆乏味的代数,并且stackoverflow不能很好地进行数学运算,所以我直接跳转到以伪代码表示的结果:
rho
作为健全性检查,您可以看到,如果if Y[i] == 1:
generate Y[i+1] as Bernoulli(p + rho * (1 - p))
else:
generate Y[i+1] as Bernoulli(p * (1 - rho))
只是生成Bernoulli(p),而与先前的值无关。正如您已经在问题中指出的那样,伯努利RV是具有rho = 0
的二项式。
这适用于所有n = 1
。对于负相关,0 <= rho, p <= 1
和p
的相对大小受到限制,因此伯努利斯的参数始终在0和1之间。
您可以分析检查条件概率来确认正确性。我不使用Stata,但是我在JMP statistical software中对其进行了相当全面的测试,它的工作原理很吸引人。
实施(Python)
rho
我运行了此命令并将结果重定向到文件,然后将文件导入JMP。将其作为时间序列进行分析:
样本平均值为0.69834,标准偏差为0.4589785 [该图的右上方]。自相关和部分相关的lag-1估计值为0.5011 [分别位于左下方和右下方]。如演示程序中所指定,这些估计值都是与import random
def Bernoulli(p):
return 1 if random.random() <= p else 0 # yields 1 w/ prob p, 0 otherwise
N = 100000
p = 0.7
rho = 0.5
last_y = Bernoulli(p)
for _ in range(N):
if last_y == 1:
last_y = Bernoulli(p + rho * (1 - p))
else:
last_y = Bernoulli(p * (1 - rho))
print(last_y)
的Bernoulli(0.7)的极佳匹配。
如果目标是产生具有指定相关性的(X,Y)对,则将循环修改为:
rho = 0.5
答案 1 :(得分:2)
这是@pjs在Stata中的解决方案,用于生成变量的 对 :
clear
set obs 100
set seed 12345
generate x = rbinomial(1, 0.7)
generate y = rbinomial(1, 0.7 + 0.2 * (1 - 0.7)) if x == 1
replace y = rbinomial(1, 0.7 * (1 - 0.2)) if x != 1
summarize x y
Variable | Obs Mean Std. Dev. Min Max
-------------+---------------------------------------------------------
x | 100 .72 .4512609 0 1
y | 100 .67 .4725816 0 1
correlate x y
(obs=100)
| x y
-------------+------------------
x | 1.0000
y | 0.1781 1.0000
和模拟:
set seed 12345
tempname sim1
tempfile mcresults
postfile `sim1' mu_x mu_y rho using `mcresults', replace
forvalues i = 1 / 100000 {
quietly {
clear
set obs 100
generate x = rbinomial(1, 0.7)
generate y = rbinomial(1, 0.7 + 0.2 * (1 - 0.7)) if x == 1
replace y = rbinomial(1, 0.7 * (1 - 0.2)) if x != 1
summarize x, meanonly
scalar mean_x = r(mean)
summarize y, meanonly
scalar mean_y = r(mean)
corr x y
scalar rho = r(rho)
post `sim1' (mean_x) (mean_y) (rho)
}
}
postclose `sim1'
use `mcresults', clear
summarize *
Variable | Obs Mean Std. Dev. Min Max
-------------+---------------------------------------------------------
mu_x | 100,000 .7000379 .0459078 .47 .89
mu_y | 100,000 .6999094 .0456385 .49 .88
rho | 100,000 .1993097 .1042207 -.2578483 .6294388
请注意,在此示例中,我改用p = 0.7
和rho = 0.2
。
答案 2 :(得分:2)
这是@pjs在Stata中的解决方案,用于生成 时间序列 :
clear
set seed 12345
set obs 1
local p = 0.7
local rho = 0.5
generate y = runiform()
if y <= `p' replace y = 1
else replace y = 0
forvalues i = 1 / 99999 {
set obs `= _N + 1'
local rnd = runiform()
if y[`i'] == 1 {
if `rnd' <= `p' + `rho' * (1 - `p') replace y = 1 in `= `i' + 1'
else replace y = 0 in `= `i' + 1'
}
else {
if `rnd' <= `p' * (1 - `rho') replace y = 1 in `= `i' + 1'
else replace y = 0 in `= `i' + 1'
}
}
结果:
summarize y
Variable | Obs Mean Std. Dev. Min Max
-------------+---------------------------------------------------------
y | 100,000 .70078 .4579186 0 1
generate id = _n
tsset id
corrgram y, lags(5)
-1 0 1 -1 0 1
LAG AC PAC Q Prob>Q [Autocorrelation] [Partial Autocor]
-------------------------------------------------------------------------------
1 0.5036 0.5036 25366 0.0000 |---- |----
2 0.2567 0.0041 31955 0.0000 |-- |
3 0.1273 -0.0047 33576 0.0000 |- |
4 0.0572 -0.0080 33903 0.0000 | |
5 0.0277 0.0032 33980 0.0000 | |