Bagaimana saya bisa mengambil sampel dari distribusi dengan CDF yang tidak dapat dihitung?

8

Simulasi ilmu semi-komputer terkait masalah di sini.

Saya punya distribusi di mana

P (x) =(eb1)eb(nx)ebn+b1

untuk beberapa konstanta b dan n, dan x adalah bilangan bulat sehingga .0xn

Sekarang, saya perlu sampel dari distribusi ini. Ini memiliki CDF yang dapat dibalik, jadi dimungkinkan untuk melakukan ini secara langsung dalam teori. Masalahnya adalah bahwa angka-angka yang terlibat adalah BESAR. Begitu besar pada kenyataannya, bahwa mereka berdua meluap variabel diformat secara konvensional, dan mengambil setidaknya beberapa menit (pada titik tertentu saya menyerah ...) untuk menghitung menggunakan format presisi sewenang-wenang. Pada dasarnya, CDF terbalik masih melibatkan istilah , untuk . Meskipun demikian, angka-angka output masih akan berada dalam kisaran , jadi sepertinya harus ada cara untuk melakukan ini.eb(n+1)350<n<35000n

Apa yang saya cari adalah cara kira-kira pengambilan sampel dari distribusi ini yang dapat dihitung. Apakah ada metode pengambilan sampel alternatif? Apakah mereka?

John Doucette
sumber
2
Sudahkah Anda mempertimbangkan normalisasi atau penskalaan data dengan cara tertentu untuk mengurangi domain?
EngrStudent

Jawaban:

7

CDF siap dibalik. Formula untuk inversi mengarah pada apa yang harus menjadi salah satu solusi yang paling sederhana dan paling bijaksana.

Mulailah dengan mengamati bahwa kemungkinan hasilnya k, 0kn, sebanding dengan ebk. Jadi, jika kita menghasilkan nilai yang seragamq antara 0 dan qmax=k=0nebk= , kita hanya perlu menemukan terbesar yang(1eb(n+1))/(1eb)k

qi=0kebi=1e(k+1)b1eb.

Aljabar sederhana memberikan solusinya

k=ceiling(log(1q(1eb))b).

Berikut ini adalah Rimplementasi yang dibangun seperti semua generator bilangan acak lainnya: argumen pertamanya menentukan berapa banyak nilai iid yang akan dihasilkan dan argumen lainnya menamai parameter ( as dan as ):bbnn.max

rgeom.truncated <- function(n=1, b, n.max) {
  a <- 1 - exp(-b)
  q.max <- (1 - exp(-b*(n.max+1))) / a
  q <- runif(n, 0, q.max)
  return(-ceiling(log(1 - q*a) / b))
}

Sebagai contoh penggunaannya, mari kita hasilkan satu juta variasi acak menurut distribusi ini:

b <- 0.001
n.max <- 3500
n.sim <- 10^6
set.seed(17)
system.time(sim <- rgeom.truncated(n.sim, b,n.max))

( detik diperlukan.)0.10

h <- hist(sim+1, probability=TRUE, breaks=50, xlab="Outcome+1")
pmf <- exp(-b * (0: n.max)); pmf <- pmf / sum(pmf)
lines(0:n.max, pmf, col="Red", lwd=2)

Histogram

( ditambahkan ke setiap nilai dalam rangka menciptakan histogram yang lebih baik: 's prosedur memiliki keistimewaan (= bug) di mana bar pertama adalah terlalu tinggi ketika endpoint kiri ditetapkan pada nol.) Kurva merah adalah distribusi referensi bahwa simulasi ini mencoba mereproduksi. Mari kita evaluasi kebaikan fit dengan uji chi-square:1Rhist

observed <- table(sim)
expected <- n.sim * pmf
chi.square <- (observed-expected)^2 / expected
pchisq(sum(chi.square), n.max, lower.tail=FALSE)

Nilai p adalah : sangat pas.0.84

whuber
sumber
3
Solusi bagus Saya tidak pernah tahu orang bisa mengambil sampel dengan cara ini (yaitu, mengandalkan sampel dari bukannya ), tetapi jelas dalam retrospeksi. Uni(0,k),k>1Uni(0,1)
Cam.Davidson.Pilon
6

Anda sedang berhadapan dengan distribusi geometris terpotong dengan . Ada berbagai cara untuk mendekati ini.p=1eb

Saya akan menyarankan opsi yang berbeda dalam situasi yang berbeda; beberapa opsi akan melibatkan simulasi dari geometrik dan regenerasi ketika berada di luar rentang, mengambil bagian integer dari eksponensial terpotong yang sesuai ( seperti di sini ), atau menggunakan salah satu dari beberapa teknik cepat yang dirancang untuk distribusi diskrit pada rentang yang terbatas. Mengingat bahwa besar, mengambil dasar dari eksponensial terpotong cenderung relatif cepat, tetapi apakah itu pilihan terbaik juga tergantung pada .nb

Ini pertanyaan terkait tentang math.SE

Sebelum saya mencoba saran spesifik, apa kisaran nilai khas untuk ?b

Glen_b -Reinstate Monica
sumber
Terima kasih atas jawaban anda! b ~ ln (1 + epsilon), di mana epsilon adalah parameter tambahan> 0.
John Doucette
1
Jadi, Anda telah mengonversi pertanyaan saya tentang kisaran b untuk satu tentang kisaran khas ε. Sebelum saya mencoba saran spesifik, apa kisaran nilai khas untuk ε?
Glen_b -Reinstate Monica
Alasan saya bertanya adalah pendekatan mana yang lebih efisien tergantung pada karakteristik situasi. Sepertinya Anda sudah senang dengan jawaban yang lain, jadi mungkin tidak perlu khawatir tentang potensi efisiensi tambahan.
Glen_b -Reinstate Monica
@ JohnDoucette: Jika b hampir nol maka distribusi Anda hampir seragam di atas maka Anda dapat menggunakan seragam sebagai proposal dalam algoritma accept accept karena batas atas seharusnya tidak terlalu buruk. {0,,n\]
Xi'an
1
@ Xi'an Anda perlu cukup kecil daripada sebelum akan sesuai untuk menggunakan distribusi yang seragam, karena tingkat penerimaannya adalah , yang akan menjadi tidak efisien ketika . nbb0(1e(n+1)b)/((n+1)(1eb)) (1exp(nb))/(nb)nb1
whuber
4

Pertama, perhatikan bahwa yang, jika kontinu, akan terkait dengan distribusi eksponensial. Kemudian, apa yang dapat Anda lakukan adalah mensimulasikan dari distribusi eksponensial terpotong dan mengambil (bagian integer) pengamatan.P(x)ebxxfloor()

Cdf dari eksponensial terpotong adalah

F(x;n,b)=1ebx1ebn.

Kemudian, jika kita membuat , kita memperoleh . Jika besar, maka yang menyarankan untuk mendekati .F(x;n,b)=ux=1blog[1u(1ebn)]bnebn0x1blog[1u]

rweirdp <- function(ns,n,b){
u <- runif(ns)
samp <- - log(1-u*(1-exp(-n*b)))/b
return(floor(samp))
}

rweirdp(1000,10,1)
Orang
sumber
Saya pikir ini pada dasarnya apa yang saya cari. bn selalu sangat besar, pengambilan sampel proporsional masuk akal. Tidak menyadari pemetaan, meskipun jelas dalam retrospeksi. Terima kasih!
John Doucette
Saya senang melihat itu membantu. Saya pikir saya tidak menjelaskan dengan baik tetapi pendekatan ini menghasilkan sampel dari distribusi target yang tepat. Bersulang.
Orang
@ Xi'an Bukankah bobotnya sama jika seseorang menggunakan nilai dan mengambil bagian integer? ebn
Orang
@ Xi'an Saya pikir istilah itu muncul dalam pembilang , hingga factorisation ...P(x)
Orang
1
@ Xi'an. Sebenarnya, karya yang disediakan rweirdpini diubah untuk diubah nmenjadi n+1. (Seperti yang diberikan di sini, itu tidak akan pernah mengembalikan nilai yang sama dengan n: yaitu efek perkiraan). Analisis yang sedikit lebih ketat diberikan dalam jawaban saya. Meskipun saya mendapatkan formula yang berbeda, itu setara dengan (lebih sederhana!) Yang diberikan di sini, setelah n-> n+1modifikasi dibuat.
whuber
4

Cara untuk mengambil sampel dari target distribusi adalah denganp(k)exp{bk}

  1. menjalankan eksperimen Metropolis-Hastings untuk menentukan (menarik) dukungan dari distribusi, yaitu di mana subset dari terkonsentrasi;{0,1,,n}

    metro=function(N,b,n){
    x=sample(0:n,N,rep=TRUE)
    for (t in 2:N){
      x[t]=prop=x[t-1]+sample(c(-1,1),1)
    
      if ((prop<0)||(prop>n)||(log(runif(1))>b*(x[t]-prop)))
          x[t]=x[t-1]
      }
    return(x)
    }
    
  2. Gunakan dukungan yang ditentukan, katakan, untuk menghitung probabilitas tepat sebagai untuk menghindari luberan.{k0,,k1}p(k)exp{bk+bk0}

Pembaruan: Ketika memikirkan lebih lanjut tentang itu, karena berkurang dalam k, dukungan distribusi yang efektif akan selalu dimulai pada . Jika cukup besar, dukungan ini akan berakhir dengan sangat cepat, dalam hal ini tidak menjadi masalah karena nilai tidak akan pernah dikunjungi. Jika sangat kecil, pdfnya hampir datar, yang berarti bahwa seseorang dapat menggunakan distribusi seragam pada sebagai proposal accept-reject. Dan gunakan log pada langkah penerimaan untuk menghindari luapan.p()k0=0bnkb{0,1,,n}

Xi'an
sumber