Combinatorics - calculating probability of choosing n people from m groups of k people I am trying to calculate and understand the following question:
I have 10 groups of 10 people each and am choosing 10 people at random.  What is the probability that all 10 people I have chosen are from one group? From 2 groups? Etc.

Consider $m=10$ groups of size $n=10$ each.  Obtain a sample of size $N$ by withdrawing one element at a time.  For the possible counts $0, 1, 2, \ldots, m,$ let $p_N(i)$ be the chance that exactly $i$ groups are represented in this sample.
Notice, now, that when $i$ groups are represented in a sample of size $N,$ there remain $nm-N$ unsampled elements, of which $in-N$ are in the groups appearing in the sample.  The chance of selecting one of these at the next step is therefore $(in-N)/(nm-N)$, while the chance of selecting a different one--and thereby increasing $i$ to $i+1$--is $1 - (in-N)/(nm-N).$ Consequently, the $p_N(i)$ enjoy the recursive relationship
$$p_{N+1}(i) = p_N(i) \left(\frac{ni-N}{nm-N}\right) + p_N(i-1)\left(1 - \frac{n(i-1)-N}{nm-N}\right).$$
At the beginning, with a sample size of $1,$ clearly $p_1(1)=1$ and all the other $p_1(i)=0.$  Updating this vector of length $m+1$ $N-1$ times requires only $(m+1)(N-1)$ of the foregoing calculations.  That's efficient.  (Well before $m$ and $n$ become large enough to make this onerous, asymptotic approximations will become highly accurate.)
Here is R code to carry out this simple calculation:
n <- 10 # Group size
m <- 10 # Number of groups
N <- 10 # Sample size

P <- c(0, 1, rep.int(0, m-1))
i <- seq_len(m)
for (k in seq_len(N)[-1] - 1) 
  P <- c(0, (P[i + 1] * (n * i - k) + P[i] * n * (m - i + 1)) / (n * m - k))

As a test, let's compare it to a direct, brute-force simulation of a half million samples.
set.seed(17)
pop <- rep.int(seq_len(m), n)                             # The elements to sample
x <- replicate(5e5, sum(tabulate(sample(pop, N), m) > 0)) # Take the samples
simulation <- c(0, tabulate(x, m) / length(x))            # Compute frequencies
names(simulation) <- c(0, seq_len(m))                     # Adjoin column headings
rbind(simulation, P)                                      # Compare to the calculation


           0        1       2        3       4      5     6     7     8      9       10
simulation 0 0.00e+00 0.0e+00 0.000226 0.00865 0.0928 0.313 0.389 0.172 0.0234 0.000572
P          0 5.78e-13 4.8e-07 0.000204 0.00884 0.0922 0.314 0.389 0.172 0.0234 0.000578


The headers are the group counts.  You can see the agreement is good.

