Stata The Stata listserver
[Date Prev][Date Next][Thread Prev][Thread Next][Date index][Thread index]

st: RE: generation of random numbers to generate CDF


From   "Nick Cox" <n.j.cox@durham.ac.uk>
To   <statalist@hsphsun2.harvard.edu>
Subject   st: RE: generation of random numbers to generate CDF
Date   Mon, 15 Sep 2003 11:37:17 +0100

Clint Thompson wrote, modulo XML,

> I wrote a program with Intercooled STATA V8 that
> generates random numbers from an exponential distribution,
> from which I want to standardize the random numbers then
> compare the distribution to the Standard Normal CDF.
> If I limit the number of observations to 100 and the number
> of iterations to 100 the program runs fine, but if I want to
> increase the number of iterations to 1,000 STATA returns an
> error indicating that the matsize is too small - a predictable
> response since Intercooled limits the matsize to 800.  I've
> pasted my code below and I'm wondering if anyone has any
> suggestions regarding a more elegant way to write the program
> or if I simply have to accept the fact that Intercooled STATA 8
> won't generate the 1,000 iterations.  Many thanks in advance.

> Here is the code for 100 observations and 100 iterations,
> which runs fine, but how to address the need to iterate 1,000
> or more times (that is, change the N to 1,000)??

> /*   N = 100 ITERATIONS */
> /*  EXPONENTIAL, N=100  */
> forvalues i = 1(1)100 {
>      set obs 100
>      generate exp`i' = -1*ln(uniform())
>      }
> set matsize 100
> collapse (mean) exp1-exp100         /*Returns a 1x100 vector of
means*/
> mkmat exp1-exp1000, matrix(Means)
> matrix Means_T = Means'             /*Returns transpose of above
matrix*/
> matrix one = J(100,1,1)             /*Creates 100x1 matrix w/all
ones in column*/
> matrix Ysubn = (Means_T - one)*(sqrt(100))      /*Generate the Ys*/
> svmat double Ysubn, name(Yexp100)   /*Changes the col.vector to a
variable */
> drawnorm norm100, n(100)            /*Draws random sample from
normal distribution*/
> cumul Yexp1001, gen(EXP100)         /*cumulative distribution
function*/
> cumul norm100, gen(NORM_100)        /*cumulative dist. function for
Std. Normal*/
> label var EXP100 "Exponential, N=100"
> label var NORM_100 "Standard Normal, N=100"
> #delimit ;
> /*Dual CDF plots*/
> line EXP100 Yexp1001, clwidth(medthick) || line NORM_100 norm100,
sort
> clwidth(thick) xtick(-4.0(.5)4.0);
> clear

I don't think you need use Stata's matrices at all.
Nor should you loop over repeated samples.
Just generate your random numbers _once_ as two
variables and then subdivide into blocks.

set obs 100000
gen exp = -ln(uniform())
gen norm = invnorm(uniform())
egen id = seq(), block(1000)

etc.

A quite different comment is that I am not
clear that you need use random numbers
for whatever it is you want to do. There
may be an analytic solution.

Nick
n.j.cox@durham.ac.uk

*
*   For searches and help try:
*   http://www.stata.com/support/faqs/res/findit.html
*   http://www.stata.com/support/statalist/faq
*   http://www.ats.ucla.edu/stat/stata/



© Copyright 1996–2021 StataCorp LLC   |   Terms of use   |   Privacy   |   Contact us   |   What's new   |   Site index