# How to generate an arbitrary discrete distribution? (EmpiricalDistribution vs ProbabilityDistribution)

I've just started using Mma's distributions. Suppose I want to generate an arbitrary discrete distribution by matching probabilities to outcomes.

p = {.4, .2, .3, .1}
vals = {0, 2, 3, 99}


This does not seem to be easy with ProbabilityDistribution, partly because it does not accept a List iterator. However, it seems I can use EmpiricalDistribution as follows:

mydist = EmpiricalDistribution[p -> vals];


Is this in any way an abuse? It seems to behave as I hoped.

Now someone might say, why not use MultinomialDistribution. E.g.,

mydist02 = MultinomialDistribution[1, p]


But I think that's not quite as convenient because believe I will have to Pick from my vals using the returned List. Or am I missing something?

• That is a completely valid use of EmpiricalDistribution, and is documented as such. You can also do it with ProbabilityDistribution, but more bother for such simple cases. – ciao Sep 25 '15 at 4:21
• BTW- if all that matters is generating variates, just use RandomChoice - cleaner. – ciao Sep 25 '15 at 4:26

Next to using EmpiricalDistribution the way you have done, you may build arbitrary discrete distribution by giving the definition of the PDF.
probs = {0.4, 0.2, 0.3, 0.1};
pdf = Piecewise@Inner[ Function[ {p, v}, {p, $FormalX] == v} ], probs, vals, List ]; dist = ProbabilityDistribution[ pdf, {\[FormalX], 0, 100, 1} ]; PDF[ dist, 0 ]  0.4 Histogram[ RandomVariate[ dist, 10000 ], {0, 100, 1}, "PDF" ]  As an aside, from the examples given in the documentation for EmpiricalDistribution I noted to use of Boole so the pdf may be given as: pdf = Inner[ Function[ {p,v}, p Boole[ \[FormalX] == v ], probs, vals, Plus ];  While using EmpiricalDistribution is maybe easier, using ProbabilityDistribution should be more general and thus allow more flexibility. As the examples hopefully have demonstrated, the setup may not be too cumbersome. By giving the option Method -> "Normalize" ProbabilityDistribution will - like EmpiricalDistribution take care of the probabilities adding up to one. • But take note of (125314) as ProbabilityDistribution seems to be broken for other stepsizes than dx = 1. – gwr Sep 1 '16 at 20:57 Perhaps you can use MultinomialDistribution in this way: mn = MultinomialDistribution\[1, {0.4, 0.3, 0.2, 0.1}]; r = Thread\[Range\[4$ -> {0, 2, 3, 99}];