Ottieni un booleano casuale in Python?


244

Sto cercando il modo migliore (veloce ed elegante) per ottenere un booleano casuale in pitone (lanciare una moneta).

Per il momento sto usando random.randint(0, 1)o random.getrandbits(1).

Ci sono scelte migliori di cui non sono a conoscenza?

Risposte:


332

La risposta di Adam è abbastanza veloce, ma ho scoperto che random.getrandbits(1)è molto più veloce. Se vuoi davvero un booleano anziché un lungo allora

bool(random.getrandbits(1))

è ancora circa due volte più veloce di random.choice([True, False])

Entrambe le soluzioni devono import random

Se la massima velocità non è prioritaria, allora random.choicelegge decisamente meglio

$ python -m timeit -s "import random" "random.choice([True, False])"
1000000 loops, best of 3: 0.904 usec per loop
$ python -m timeit -s "import random" "random.choice((True, False))" 
1000000 loops, best of 3: 0.846 usec per loop
$ python -m timeit -s "import random" "random.getrandbits(1)"
1000000 loops, best of 3: 0.286 usec per loop
$ python -m timeit -s "import random" "bool(random.getrandbits(1))"
1000000 loops, best of 3: 0.441 usec per loop
$ python -m timeit -s "import random" "not random.getrandbits(1)"
1000000 loops, best of 3: 0.308 usec per loop
$ python -m timeit -s "from random import getrandbits" "not getrandbits(1)"
1000000 loops, best of 3: 0.262 usec per loop  # not takes about 20us of this

Aggiunto questo dopo aver visto la risposta di @ Pavel

$ python -m timeit -s "from random import random" "random() < 0.5"
10000000 loops, best of 3: 0.115 usec per loop

14
Se si tratta di prestazioni, not not random.getrandbits(1))è più veloce di bool;)
Michał Bentkowski il

11
Probabilmente non hai nemmeno bisogno di lanciare un booleano, poiché 0/1 ha i valori di verità corretti.
Adam Vandenberg,

6
Si potrebbe accelerare ulteriormente facendo from random import getrandbitsper evitare la ricerca degli attributi. :-)
kindall


40

Trovato un metodo più veloce:

$ python -m timeit -s "from random import getrandbits" "not getrandbits(1)"
10000000 loops, best of 3: 0.222 usec per loop
$ python -m timeit -s "from random import random" "True if random() > 0.5 else False"
10000000 loops, best of 3: 0.0786 usec per loop
$ python -m timeit -s "from random import random" "random() > 0.5"
10000000 loops, best of 3: 0.0579 usec per loop

3
random() > 0.5valuta già un bool che è ancora più veloce!
John La Rooy

26
random() >= 0.5, altrimenti sarai un po 'di parte nei confronti di False.
Simon Lindholm,

17
random() < 0.5ha più senso se il passaggio da 0,5 ad altre probabilità funziona come previsto
akxlr il


8

Se vuoi generare un numero di booleani casuali puoi usare il modulo casuale di numpy. Dalla documentazione

np.random.randint(2, size=10)

restituirà 10 numeri interi casuali nell'intervallo aperto [0,2). La sizeparola chiave specifica il numero di valori da generare.


Ero curioso di sapere come la velocità di questo metodo ha funzionato rispetto alle risposte poiché questa opzione è stata lasciata fuori dai confronti. Per generare un bool casuale (che è la domanda) questo è molto più lento ma se si desidera generarne molti, questo diventa molto più veloce: $ python -m timeit -s "da importazione casuale random" "random () <0,5" 10000000 loop , meglio di 3: 0,0906 usec per loop
ojunk

2

Ero curioso di sapere come si è comportata la velocità della risposta insensibile rispetto alle altre risposte poiché questa è stata lasciata fuori dai confronti. Per generare un bool casuale questo è molto più lento ma se si desidera generarne molti, questo diventa molto più veloce:

$ python -m timeit -s "from random import random" "random() < 0.5"
10000000 loops, best of 3: 0.0906 usec per loop
$ python -m timeit -s "import numpy as np" "np.random.randint(2, size=1)"
100000 loops, best of 3: 4.65 usec per loop

$ python -m timeit -s "from random import random" "test = [random() < 0.5 for i in range(1000000)]"
10 loops, best of 3: 118 msec per loop
$ python -m timeit -s "import numpy as np" "test = np.random.randint(2, size=1000000)"
100 loops, best of 3: 6.31 msec per loop


0

Una nuova interpretazione di questa domanda implicherebbe l'uso di Faker con il quale è possibile installarlo facilmente pip.

from faker import Factory

#----------------------------------------------------------------------
def create_values(fake):
    """"""
    print fake.boolean(chance_of_getting_true=50) # True
    print fake.random_int(min=0, max=1) # 1

if __name__ == "__main__":
    fake = Factory.create()
    create_values(fake)

14
Dovresti almeno spiegare perché pensi che questa sia una soluzione migliore, considerando che implica il download di un pacchetto diverso ed è più disordinata.
Bzazz,

2
Non sono d'accordo con i voti negativi. Se stai creando dati casuali, potresti trovarti in una situazione in cui Faker è uno strumento molto utile. La fake.boolean()sintassi è pulita e facile per gli altri grok.
Jason McVetta,

3
Indipendentemente dal fatto che il pacchetto sia utile o meno, la completa mancanza di spiegazioni sul perché si dovrebbe considerare questo rende la risposta inutile.
Apollys supporta Monica il
Utilizzando il nostro sito, riconosci di aver letto e compreso le nostre Informativa sui cookie e Informativa sulla privacy.
Licensed under cc by-sa 3.0 with attribution required.