int ranhprob(int n, int a, int m) // hypergeometric sampling // rejection sampling. Devroye. Computing (1987) General method for log-concave densities // where mode is known /** urn with n balls . a black balls. Pick m without replacement. Return number of black balls picked. */ { double y ; double pm, logpm, w, ru, rw, rat ; int mode, x, zans ; mode = modehprob(n, a, m) ; logpm = loghprob(n, a, m, mode) ; pm = exp(logpm) ; w = 1 + pm ; for (;;) { ru = DRAND() ; rw = DRAND() ; if (ru <= w/(1+w)) y = DRAND()*w/pm ; else y = (w+ranexp())/pm ; x = nnint(y) ; if (ranmod(2)==0) x = -x ; zans = mode+x ; if (zans<0) continue ; if (zans>a) continue ; rat = exp(loghprob(n, a, m, zans)-logpm) ; rw *= MIN(1, exp(w-pm*y)) ; if (rw <= rat) break ; } return zans ; }
double rangam(double a) { /** generate gamma deviate mean a */ if (a < 1.0) { return( randev0(a)); } if (a == 1.0) { return( ranexp()); } return( randev1(a)); }
double rangam(double a) { /** generate gamma deviate mean a */ if (a<=0.0) { fatalx("rangam called with bad param. a: %9.3f\n", a) ; } if (a < 1.0) { return( randev0(a)); } if (a == 1.0) { return( ranexp()); } return( randev1(a)); }
int ranhprob(int n, int a, int m) // rejection sampling. Devroye { double v, y ; double pm, logpm, w, ru, rw, rat ; int mode, k, x, zans ; v = (double) (a+1)*(m+1) / (double) (n+1) ; mode = (int) v ; /** for (k=-5; k<=5; ++k) { x = mode+k ; y = exp(loghprob(n, a, m, x)) ; printf("%4d %4d %12.6f\n", mode, x, y) ; } */ logpm = loghprob(n, a, m, mode) ; pm = exp(logpm) ; w = 1 + pm ; for (;;) { ru = DRAND() ; rw = DRAND() ; if (ru <= w/(1+w)) y = DRAND()*w/pm ; else y = (w+ranexp())/pm ; x = nnint(y) ; if (ranmod(2)==0) x = -x ; zans = mode+x ; if (zans<0) continue ; if (zans>a) continue ; rat = exp(loghprob(n, a, m, zans)-logpm) ; rw *= MIN(1, exp(1.0-pm*y)) ; if (rw <= rat) break ; } return zans ; }