Özel ortalama ve standart sapma gibi belirli kısıtlamaları sağlayan veriler nasıl simüle edilir?


56

Bu soru meta-analiz konusundaki sorumum tarafından motive edildi . Ancak, mevcut bir yayınlanmış veri setini tam olarak yansıtan bir veri seti oluşturmak istediğiniz bağlamları öğretmede de faydalı olacağını hayal ediyorum.

Belirli bir dağıtımdan rasgele veri üretmeyi biliyorum. Örneğin, bir çalışmanın sonuçlarını okuduysanız:

  • 102 ortalama,
  • 5.2 standart bir sapma ve
  • 72 örneklem büyüklüğü.

rnormR kullanarak benzer veri üretebilir.

set.seed(1234)
x <- rnorm(n=72, mean=102, sd=5.2)

Tabii ki ortalama ve SD sırasıyla 102 ve 5.2'ye tam olarak eşit olmaz:

round(c(n=length(x), mean=mean(x), sd=sd(x)), 2)
##     n   mean     sd 
## 72.00 100.58   5.25 

Genel olarak, bir dizi kısıtlamaya uyan verinin nasıl simüle edileceği ile ilgileniyorum. Yukarıdaki durumda, sınırlar örneklem büyüklüğü, ortalama ve standart sapmadır. Diğer durumlarda, ek kısıtlamalar olabilir. Örneğin,

  • Verilerde veya temel değişkende minimum ve maksimum olarak bilinir.
  • değişkenin yalnızca tam sayı değerlerini veya yalnızca negatif olmayan değerleri aldığı bilinmektedir.
  • Veriler bilinen korelasyonları olan çoklu değişkenler içerebilir.

Sorular

  • Genel olarak, bir dizi kısıtlamayı tam olarak karşılayan verileri nasıl simüle edebilirim?
  • Bununla ilgili yazılmış makaleler var mı? R'de bunu yapan herhangi bir program var mı?
  • Örnek olarak, bir değişkeni belirli bir ortalama ve sd'ye sahip olacak şekilde nasıl simüle edebilirim ve etmeliyim?

1
Neden tam olarak yayınlanan sonuçlara benzemelerini istiyorsun? Verilere örnek olarak verilen nüfus ortalaması ve standart sapma tahminleri bu değildir. Bu tahminlerdeki belirsizlik göz önüne alındığında, yukarıda gösterilmiş olan örneklemin gözlemleriyle tutarlı olmadığını kim söyleyebilir?
Gavin Simpson,

4
Bu soru, işareti (IMHO) özleyen cevapları toplamak gibi göründüğü için, kavramsal olarak cevabın basit olduğunu belirtmek isterim: eşitlik kısıtlamaları, marjinal dağılımlar gibi ele alınır ve eşitsizlik kısıtlamaları çok değişkenli kesilme analoglarıdır. Kısaltmanın kullanımı nispeten kolaydır (genellikle ret örneklemeyle); daha zor olan problem ise bu marjinal dağılımları örneklemenin bir yolunu bulmaktır. Bu, dağıtım ve kısıtlama verilen marjinalleri örnekleme veya ondan gelen marjinal dağılımı ve örneklemeyi bulmak için entegrasyon anlamına gelir.
whuber

4
BTW, son soru lokasyon ölçekli dağıtım aileleri için önemsizdir. Örneğin, x<-rnorm(72);x<-5.2*(x-mean(x))/sd(x)+102numara yapar.
whuber

1
@whuber, kardinal, cevabımın bir yorumuna (bu "hile" den bahseder) ve başka bir cevaba bir yorumda bulunmaya itiraz eder - bu yöntem, genel olarak, bölüştüğünüz için değişkenleri aynı dağıtım ailesinde tutmaz Örnek standart sapma ile.
Makro

5
@ Makro Bu iyi bir nokta, ama belki de en iyi cevap, "elbette aynı dağılıma sahip olmayacaklar" dır! İstediğiniz dağıtım dağıtım koşullu kısıtlamalar üzerinde. Genel olarak bu ebeveyn dağılımı ile aynı aileden olmayacak. Örneğin, normal dağılımdan çizilen ortalama 0 ve SD1 olan 4 büyüklüğünde bir numunenin her bir elemanı [-1.5, 1.5] ' de neredeyse eşit bir olasılıkta olacaktır, çünkü koşullar muhtemel değerlere üst ve alt sınırlar koyar.
whuber

Yanıtlar:


26

Genel olarak, numunenizi önceden belirlenmiş bir değere tam olarak eşit ve değişken yapmak için , değişkeni uygun şekilde kaydırıp ölçeklendirebilirsiniz. Spesifik olarak, eğer bir örnek ise, o zaman yeni değişkenlerX1,X2,...,Xn

Zi=c1(XiX¯sX)+c2

burada örneklem ortalamasıdır ve , örnek varyansıdır, 'nin örnek ortalaması tam olarak ve örnek varyansı tam olarak . Benzer şekilde inşa edilmiş bir örnek menzili sınırlayabilir -s 2 x =1X¯=1ni=1nXiZic2c1sX2=1n1i=1n(XiX¯)2Zic2c1

Bi=a+(ba)(Ximin({X1,...,Xn})max({X1,...,Xn})min({X1,...,Xn}))

aralığıyla sınırlı olan veri kümesini . ( a , b )B1,...,Bn(a,b)

Not: Bu tür kaydırma / ölçekleme, genel olarak, orijinal veriler yer ölçeğinde bir aileden gelse bile, verilerin dağılım ailesini değiştirir.

Kapsamında normal dağılımmvrnorm fonksiyonu R Eğer önceden belirlenmiş bir normal (veya normal değişkenli) veri taklit sağlar örnek ayarlayarak / kovaryans ortalama empirical=TRUE. Spesifik olarak, bu fonksiyon , numune ortalaması ve (co) varyansının önceden belirlenmiş bir değere eşit olması koşuluyla normal dağılıma ait bir değişkenin koşullu dağılımından gelen verileri simüle eder . Elde edilen marjinal dağılımların , ana soruya yapılan bir yorumda @whuber tarafından belirtildiği gibi normal olmadığını unutmayın.

Örnek ortalamasının ( 4'lük bir örnekten ) 0 olması ve örnek standart sapmanın 1 olmasıyla sınırlandırıldığı basit tek değişkenli bir örnek. İlk elemanın normal dağılıma göre eşit dağılıma çok daha yakın olduğunu görebiliriz. dağıtım:n=4

library(MASS)
 z = rep(0,10000)
for(i in 1:10000)
{
    x = mvrnorm(n = 4, rep(0,1), 1, tol = 1e-6, empirical = TRUE)
    z[i] = x[1]
}
hist(z, col="blue")

                  görüntü tanımını buraya girin


1
örnek boyutu büyük ise, bu şekilde de yaklaşık olabilir ama normal olarak, dağıtılan edilmeyecektir. @ Sean'ın cevabına ilk yorum, bu ima. Zi
kardinal

1
Eh, bu neden olmaz çoğu zaman ... oldukça doğal bir şey yapmak istiyorum içelim ve çok fazla sorun.
kardinal

1
+1. Örnekte, üniforma bu arada kesin cevaptır. (
Grafiğin sonundaki belirgin düşme,

1
@whuber, bu örneği motive ettiğin için teşekkürler. Marjinal dağılımların, örnek ortalama / varyansına şart koyduğunuzda değiştiği göz önüne alındığında, OP'nin sorusu çerçevesinde en iyi "cevap", sadece örnek olarak bildirilene eşit nüfus ortalaması / varyansı ile verileri simüle etmek görünüyor miktarlar (OP'nin önerdiği gibi), değil mi? Bu şekilde, istenen miktarlara "benzer" örnek miktarları alırsınız ve marjinal dağılımlar sizin olmasını istediğiniz şeydir.
Makro

1
Numunenin normal ise @whuber, daha sonra bir sahiptir evet -Dağıtım? Söz konusu "yeni" değişken sadece doğrusal bir birleşimi olacaktır . t T iTi=(XiX¯)/stTi
Makro

22

Bildiri talebinizle ilgili olarak:

Bu tam olarak aradığınız şey değil, ancak değirmen için bir zafer görevi görebilir.


Kimsenin bahsetmediği başka bir strateji var. Kalan verileri uygun değerlerde sabitlendiği sürece tüm kümenin kısıtlamalarını karşıladığı şekilde bir büyüklüğü kümesinden (sözde) rasgele veri üretmek mümkündür . Gerekli değerler bir denklem sistemi , cebir ve bir miktar dirsek yağı ile çözülebilir olmalıdır . N k k kNkNkkk

Örneğin, belirli bir örnek ortalamasını, ve varyansı, olacak normal bir dağılımdan bir verileri kümesi oluşturmak için , iki noktanın değerlerini düzeltmeniz gerekir: ve . Örnek ortalama şu şekilde olduğundan: olmalı: Örnek sapması: , böylece (yukarıdaki ikame sonra / dağıtma folyo, ve yeniden düzenleme ... ) biz alırız: ˉ x s 2 y z ˉ x = N - 2 i = 1 x iNx¯s2yz
yy=N ˉ x

x¯=i=1N2xi+y+zN
y
y=Nx¯(i=1N2xi+z)
s2=i=1N2(xix¯)2+(yx¯)2+(zx¯)2N1
y a = - 2 b = 2 ( N ˉ x - N - 2 i = 1 x i ) c z
2(Nx¯i=1N2xi)z2z2=Nx¯2(N1)+i=1N2xi2+[i=1N2xi]22Nx¯i=1N2xi(N1)s2
Eğer , alırsak ve , olarak , ikinci dereceden formülünü kullanarak için çözebiliriz . Örneğin, içinde , aşağıdaki kod kullanılabilir: a=2b=2(Nx¯i=1N2xi)czR
find.yz = function(x, xbar, s2){
  N    = length(x) + 2
  sumx = sum(x)
  sx2  = as.numeric(x%*%x)          # this is the sum of x^2
  a    = -2
  b    = 2*(N*xbar - sumx)
  c    = -N*xbar^2*(N-1) - sx2 - sumx^2 + 2*N*xbar*sumx + (N-1)*s2
  rt   = sqrt(b^2 - 4*a*c)

  z    = (-b + rt)/(2*a)
  y    = N*xbar - (sumx + z)
  newx = c(x, y, z)
  return(newx)
}

set.seed(62)
x    = rnorm(2)
newx = find.yz(x, xbar=0, s2=1)
newx                                # [1] 0.8012701  0.2844567  0.3757358 -1.4614627
mean(newx)                          # [1] 0
var(newx)                           # [1] 1

Bu yaklaşım hakkında anlaşılması gereken bazı şeyler var. İlk olarak, çalışacağı garanti edilmez. Örneğin, ilk verilerinizin , elde edilen kümenin varyansını eşit yapacak ve değerlerinin bulunmayacağı şekilde olması mümkündür . Düşünmek: y z s 2N2yzs2

set.seed(22)    
x    = rnorm(2)
newx = find.yz(x, xbar=0, s2=1)
Warning message:
In sqrt(b^2 - 4 * a * c) : NaNs produced
newx                                # [1] -0.5121391  2.4851837        NaN        NaN
var(c(x, mean(x), mean(x)))         # [1] 1.497324

İkincisi, standartlaştırma tüm değişkenlerinizin marjinal dağılımını daha homojen kılarken, bu yaklaşım sadece son iki değeri etkiler, fakat marjinal dağılımlarını çarpıtır:

set.seed(82)
xScaled = matrix(NA, ncol=4, nrow=10000)
for(i in 1:10000){
  x           = rnorm(4)
  xScaled[i,] = scale(x)
}

(arsa ekle)

set.seed(82)
xDf = matrix(NA, ncol=4, nrow=10000)
i   = 1
while(i<10001){
  x       = rnorm(2)
  xDf[i,] = try(find.yz(x, xbar=0, s2=2), silent=TRUE)  # keeps the code from crashing
  if(!is.nan(xDf[i,4])){ i = i+1 }                      # increments if worked
}

(arsa ekle)

Üçüncüsü, elde edilen örnek çok normal görünmeyebilir ; aslında 'aykırılıklara' (yani, diğerlerinden farklı bir veri üretme sürecinden gelen noktalara) sahip gibi görünebilir, çünkü esasen böyledir. Üretilen verilerden alınan örnek istatistiklerin istenen değerlere yakınlaşması ve bu nedenle daha az ayar gerektirmesi gerektiğinden, bu durum daha büyük örneklem büyüklüğüyle ilgili bir sorun olma ihtimalinin düşük olması anlamına gelir. Daha küçük örneklerde, bu yaklaşımı her zaman, oluşturulan örnek kabul edilebilir sınırların dışında (şekil, @ kardinal'in yorumu ) dışında olan şekil istatistiklerine (örn., Çarpıklık ve kurtoz) sahipse veya uzatırsa tekrar deneyen bir kabul / red algoritmasıyla birleştirebilirsiniz. sabit bir ortalama, varyans, çarpıklık vekurtosis (Ben cebiri sana bırakacağım). Alternatif olarak, az sayıda örnek üretebilir ve örneğin en küçük (örneğin) Kolmogorov-Smirnov istatistiklerini kullanabilirsiniz.

library(moments)
set.seed(7900)  
x = rnorm(18)
newx.ss7900 = find.yz(x, xbar=0, s2=1)
skewness(newx.ss7900)                       # [1] 1.832733
kurtosis(newx.ss7900) - 3                   # [1] 4.334414
ks.test(newx.ss7900, "pnorm")$statistic     # 0.1934226

set.seed(200)  
x = rnorm(18)
newx.ss200 = find.yz(x, xbar=0, s2=1)
skewness(newx.ss200)                        # [1] 0.137446
kurtosis(newx.ss200) - 3                    # [1] 0.1148834
ks.test(newx.ss200, "pnorm")$statistic      # 0.1326304 

set.seed(4700)  
x = rnorm(18)
newx.ss4700 = find.yz(x, xbar=0, s2=1)
skewness(newx.ss4700)                       # [1]  0.3258491
kurtosis(newx.ss4700) - 3                   # [1] -0.02997377
ks.test(newx.ss4700, "pnorm")$statistic     # 0.07707929S

(arsa ekle)


10

Genel teknik, kısıtlamalarınıza uymayan sonuçları reddettiğiniz 'Reddetme Yöntemi' dir. Bir tür rehberliğiniz yoksa (MCMC gibi), o zaman reddedilen bir çok durum ortaya çıkarabilir (senaryoya bağlı olarak)!

Ortalama ve standart sapma gibi bir şey arıyorsanız ve hedefinizden ne kadar uzakta olduğunuzu söylemek için bir tür mesafe ölçümü oluşturabilirsiniz, istediğiniz çıktıyı veren giriş değişkenlerini aramak için optimizasyonu kullanabilirsiniz. değerler.

Bir de çirkin biz = 0 ve standart sapma = 1 anlamına sahiptir uzunluğu 100 ile rastgele homojen vektör arayacaktır örneğin.

# simplistic optimisation example
# I am looking for a mean of zero and a standard deviation of one
# but starting from a plain uniform(0,1) distribution :-)
# create a function to optimise
fun <- function(xvec, N=100) {
  xmin <- xvec[1]
  xmax <- xvec[2]
  x <- runif(N, xmin, xmax)
  xdist <- (mean(x) - 0)^2 + (sd(x) - 1)^2
  xdist
}
xr <- optim(c(0,1), fun)

# now lets test those results
X <- runif(100, xr$par[1], xr$par[2])
mean(X) # approx 0
sd(X)   # approx 1

7
Sıfır olasılığıyla ortaya çıkan kısıtlamaları karşılamak zordur. ;-) Eldeki belirli örnek için, uygun bir kayma ve genişleme kolayca belirtilen hedeflere ulaşır , ancak böyle bir işlemle verilerin dağılımının nasıl bozulduğuna bakmak için biraz daha derin bir analiz yapmak isteyebilirsiniz.
kardinal

Teşekkürler. Kuşkusuz gözlemleri dakikadan daha az ve en fazladan daha büyük reddetmek kolay olacaktır. Ve nasıl bir optimizasyon problemi olarak tanımlayabildiğinizi anlayabiliyorum. Bazı örnekler görmek ya da daha sonra ne okuyacağınıza dair bazı önerilerde bulunmak harika olurdu.
Jeromy Anglim

1
@ cardinal - kabul edildi. Hem giriş simülasyonu numaralarının hem de çıktının dağılımlarına (yani bir histograma) bakılmalıdır, çünkü bunlar bazen çok garip görünebilir!
Sean,

9

R'de bunu yapan herhangi bir program var mı?

Runuran R paketi rasgele değişebilirlerin birçok yöntem vardır. UNU.RAN (Evrensel Üniforma Olmayan RAndom Numarası üreteci) projesinden C kütüphanelerini kullanır . Rastgele değişken nesil alanının Kendi bilgi sınırlıdır, ancak Runuran vinyet güzel bakış sağlar. Aşağıda, Runuran paketindeki skeçten alınan mevcut yöntemler yer almaktadır:

Sürekli dağılımlar:

  • Uyarlanabilir Reddetme Örneklemesi
  • Ters Dönüştürülmüş Yoğunluk Reddi
  • Ters CDF'nin Polinom İnterpolasyonu
  • Basit Üniforma Oranı Yöntemi
  • Dönüştürülmüş Yoğunluk Reddi

Ayrık dağılımlar:

  • Kesikli Otomatik Reddetme Ters Çevirme
  • Alias-Urn Yöntemi
  • Kesikli İnversiyon için Kılavuz-Tablo Yöntemi

Çok değişkenli dağılımlar:

  • Üniforma Oranı Yöntemi ile Hit-Run algoritması
  • Çok Değişkenli Naif Üniforma Oranı Yöntemi

Örnek:

Hızlı bir örnek için, 0 ile 100 arasında sınırlanmış bir Normal dağılım oluşturmak istediğinizi varsayalım:

require("Runuran")

## Normal distribution bounded between 0 and 100
d1 <- urnorm(n = 1000, mean = 50, sd = 25, lb = 0, ub = 100)

summary(d1)
sd(d1)
hist(d1)

urnorm()Fonksiyonu uygun bir sarıcı fonksiyonudur. Sahnelerin arkasında Ters CDF yönteminin Polinom İnterpolasyonu kullandığına inanıyorum ama emin değilim. Daha karmaşık bir şey için, örneğin, 0 ile 100 arasında sınırlanmış belirli bir Normal dağılım:

require("Runuran")

## Discrete normal distribution bounded between 0 and 100
# Create UNU.RAN discrete distribution object
discrete <- unuran.discr.new(pv = dnorm(0:100, mean = 50, sd = 25), lb = 0, ub = 100)

# Create UNU.RAN object using the Guide-Table Method for Discrete Inversion
unr <- unuran.new(distr = discrete, method = "dgt")

# Generate random variates from the UNU.RAN object
d2 <- ur(unr = unr, n = 1000)

summary(d2)
sd(d2)
head(d2)
hist(d2)

3

Sadece dün yayınlanan gereksinimi karşılayan bir R paketi var gibi görünüyor! simstudy Keith Goldfeld tarafından

Modelleme tekniklerini keşfetmek veya veri üreten süreçleri daha iyi anlamak için veri setlerini simüle eder. Kullanıcı değişkenler arasında bir dizi ilişki belirtir ve bu özelliklere dayanarak veri üretir. Son veri setleri, randomize kontrol denemelerinden, tekrarlanan ölçüm (boyuna) tasarımlardan ve küme randomize denemelerinden gelen verileri temsil edebilir. Eksiklik, çeşitli mekanizmalar (MCAR, MAR, NMAR) kullanılarak üretilebilir.


1
Ne skeçte ne de programın ana sayfasında kısıtlamaların tam olarak yerine getirilmesinden söz edilmez. Bu paketin neden şartlı dağıtımlardan çizim gerekliliğini karşıladığını düşünüyorsunuz?
gg,

2

i=1nf(xi)
i=1nxi=μ0i=1nxi2=σ02

2

Bu cevap, değişkenleri belirli bir aralıkta kalmaya zorlamak ve ek olarak ortalamayı ve / veya varyansı dikte etmek istediğiniz duruma başka bir yaklaşım olarak değerlendirir .

[0,1]wk[0,1]k=1Nwk=1wk=1/Nμ(0,1)0<σ2<μ(1μ)σ2x1,...,xN[0,1]

y1,...,yNN(0,1)[0,1]

xk=11+e(ykvh)

ykhvhvx1,...,xN

μ=k=1Nwk1+e(ykvh)σ2=k=1Nwk(1+e(ykvh))2(k=1Nwk1+e(ykvh))2

vhvh

μ=0.8v=1wk=1/NN=200000N(0,1)N(0,0.1)Unif(0,1) 0.8N

Örnek 1

μ=0.2wk=1/NN=2000σ=0.1,0.05,0.01N(0,1)

Örnek 2

Bunların biraz beta dağıtılmış göründüğünü unutmayın, ancak değil.


Sitemizi kullandığınızda şunları okuyup anladığınızı kabul etmiş olursunuz: Çerez Politikası ve Gizlilik Politikası.
Licensed under cc by-sa 3.0 with attribution required.