Muestra aleatoria ponderada en python

Estoy buscando una definición razonable de una funciónweighted_sample eso no devuelve solo un índice aleatorio para una lista de pesos dados (que sería algo así como

def weighted_choice(weights, random=random):
    """ Given a list of weights [w_0, w_1, ..., w_n-1],
        return an index i in range(n) with probability proportional to w_i. """
    rnd = random.random() * sum(weights)
    for i, w in enumerate(weights):
        if w<0:
            raise ValueError("Negative weight encountered.")
        rnd -= w
        if rnd < 0:
            return i
    raise ValueError("Sum of weights is not positive")

para dar una distribución categórica con pesos constantes) pero una muestra aleatoria dek&nbsp;de aquellos,sin reemplazo, Tal comorandom.sample&nbsp;se comporta en comparación conrandom.choice.

Tal comoweighted_choice&nbsp;Se puede escribir como

lambda weights: random.choice([val for val, cnt in enumerate(weights)
    for i in range(cnt)])

weighted_sample&nbsp;podría ser escrito como

lambda weights, k: random.sample([val for val, cnt in enumerate(weights)
    for i in range(cnt)], k)

pero me gustaría una solución que no me obligue a desentrañar los pesos en una lista (posiblemente enorme).

Edición: si hay algoritmos agradables que me devuelvan un histograma / lista de frecuencias (en el mismo formato que el argumentoweights) en lugar de una secuencia de índices, eso también sería muy útil.