# Draw random samples from model

so after you take say 5000 samples from a model how do you draw and example say 100 of those samples?

1 Like

Here’s a snippet of how to grab the first sample from the first chain:

``````samp = idata.posterior.sel(draw=0, chain=0)
``````

And here is a snippet to grab a single random sample from your trace:

``````  samp = idata.posterior.sel(chain=np.random.choice(range(0,num_chains)),
draw=np.random.choice(range(0,num_samples))
)

``````
1 Like

thank you! How would I specify if I wanted a specific number of random samples?

1 Like

You can either do this:

``````# number of samples to grab
n = 10
samp = idata.posterior.sel(chain=np.random.choice(range(0,num_chains,size=n)),
draw=np.random.choice(range(0,num_samples,size=n,replace=False))
)
``````

However, this will only work when `n<num_samples`. If you want more than that, you’ll have to do something like this:

``````# number of samples to grab
n = 20

# calculate how many samples that implies per chain
nperchain,rem = divmod(n, num_chains)

# make sure we have asked for a multiple of num_chains
assert(rem==0)

# generate random indicies
draw_idx = np.random.choice(np.arange(num_samples),
size=nperchain,
replace=False
)
# indices corresponding to each chain
chain_idx = np.arange(num_chains)

# get cartesian product of indices
prod = np.transpose([np.tile(chain_idx, len(draw_idx)), np.repeat(draw_idx, len(chain_idx))])

# grab samples
samps = idata.posterior.sel(chain=prod[:,0],
draw=prod[:,1]
)

``````

This generates a list of indices and then grabs the corresponding samples from each chain. That would allow you to sample anywhere from `num_chains` samples all the way up to `num_samples * num_chains` samples.

2 Likes

You’re a life saver!

1 Like

You can also use `arviz.extract_dataset`: arviz.extract_dataset — ArviZ dev documentation. There are also several examples of working with InferenceData in Working with InferenceData — ArviZ dev documentation which I think will also be helpful.

3 Likes