Výběr, vzorek a volby pro náhodný výběr prvků ze seznamu v jazyce Python.

Podnikání

Funkce choice(), sample() a choices() v modulu random standardní knihovny Pythonu lze použít k náhodnému výběru a získání prvků ze seznamu, tuple, řetězce nebo jiného objektu sekvence (náhodné vzorkování).

funkce choice() získá jeden prvek, funkce sample() a choices() získají seznam více prvků. funkce sample() je neobnovitelná extrakce bez duplicit, funkce choices() je obnovitelná extrakce s duplicitami.

Zde jsou uvedeny následující informace.

  • Náhodně vyberte jeden prvek.: random.choice()
  • Náhodný výběr více prvků (bez duplicit): random.sample()
  • Náhodný výběr více prvků (s duplicitami): random.choices()
  • Oprava osiva náhodného čísla

Náhodně vyberte jeden prvek.: random.choice()

Pomocí funkce choose() modulu random se ze seznamu náhodně vybere jeden prvek, který lze načíst.

import random

l = [0, 1, 2, 3, 4]

print(random.choice(l))
# 1

Totéž platí pro tuply a řetězce. V případě řetězců je vybrán jeden znak.

print(random.choice(('xxx', 'yyy', 'zzz')))
# yyy

print(random.choice('abcde'))
# b

Chyba, pokud je jako argument zadán prázdný seznam, tuple nebo řetězec.

# print(random.choice([]))
# IndexError: Cannot choose from an empty sequence

Náhodný výběr více prvků (bez duplicit): random.sample()

Pomocí funkce sample() modulu random můžete náhodně získat více prvků ze seznamu. Nedochází k duplikaci prvků (neobnovitelný výběr).

Prvním argumentem je seznam a druhým argumentem je počet prvků, které se mají načíst. Vrátí se seznam.

import random

l = [0, 1, 2, 3, 4]

print(random.sample(l, 3))
# [2, 4, 0]

print(type(random.sample(l, 3)))
# <class 'list'>

Pokud je druhý argument nastaven na 1, je rovněž vrácen seznam s jedním prvkem; pokud je nastaven na 0, je seznam prázdný. Je-li druhý argument roven 1, je vrácen seznam s jedním prvkem; je-li roven 0, je vrácen prázdný seznam; je-li první argument větší než počet prvků v seznamu, dojde k chybě.

print(random.sample(l, 1))
# [3]

print(random.sample(l, 0))
# []

# print(random.sample(l, 10))
# ValueError: Sample larger than population or is negative

Pokud je prvním argumentem tuple nebo řetězec, vrací se stále seznam.

print(random.sample(('xxx', 'yyy', 'zzz'), 2))
# ['xxx', 'yyy']

print(random.sample('abcde', 2))
# ['b', 'e']

Pokud se chcete vrátit k tuple nebo řetězci, použijte tuple(),join().

print(tuple(random.sample(('xxx', 'yyy', 'zzz'), 2)))
# ('xxx', 'yyy')

print(''.join(random.sample('abcde', 2)))
# dc

Všimněte si, že hodnota není posuzována, takže pokud původní seznam nebo tuple obsahuje prvky se stejnou hodnotou, existuje možnost, že bude vybrána stejná hodnota.

l_dup = [0, 0, 0, 1, 1, 1, 2, 2, 2, 3, 3, 3]

print(random.sample(l_dup, 3))
# [3, 1, 1]

Pokud se chcete vyhnout duplicitním hodnotám, můžete je pomocí funkce set() převést na množinu (typ množiny) a vyjmout pouze jedinečné prvky a poté použít funkci sample().

print(set(l_dup))
# {0, 1, 2, 3}

print(random.sample(set(l_dup), 3))
# [1, 3, 2]

Náhodný výběr více prvků (s duplicitami): random.choices()

Funkce choices() modulu random umožňuje náhodně získat více prvků ze seznamu a na rozdíl od funkce sample() umožňuje vybrat duplicitní prvky.

Funkce choices() byla přidána v jazyce Python 3.6. V dřívějších verzích není k dispozici.

Argument k určuje počet prvků, které se mají načíst. Duplikace je povolena, takže počet prvků, které se mají načíst, může být větší než počet prvků v původním seznamu.

Protože k je argument pouze s klíčovým slovem, je nutné zadat klíčové slovo, například k=3.

import random

l = [0, 1, 2, 3, 4]

print(random.choices(l, k=3))
# [2, 1, 0]

print(random.choices(l, k=10))
# [3, 4, 1, 4, 4, 2, 0, 4, 2, 0]

Výchozí hodnota k je 1; pokud je vynechána, je vrácen seznam s 1 prvkem.

print(random.choices(l))
# [1]

Argument váhy může být použit k určení váhy (pravděpodobnosti), že každý prvek bude vybrán, a typ prvků v seznamu může být int nebo float.

print(random.choices(l, k=3, weights=[1, 1, 1, 10, 1]))
# [0, 2, 3]

print(random.choices(l, k=3, weights=[1, 1, 0, 0, 0]))
# [0, 1, 1]

Argument cum_weights lze zadat také jako kumulativní váhu. Parametr cum_weights v následující ukázce kódu je ekvivalentní první váze uvedené výše.

print(random.choices(l, k=3, cum_weights=[1, 2, 3, 13, 14]))
# [3, 2, 3]

Výchozí hodnota pro argumenty weights a cum_weights je None, což znamená, že každý prvek je vybrán se stejnou pravděpodobností.

Pokud se délka (počet prvků) argumentu weights nebo cum_weights liší od původního seznamu, dojde k chybě.

# print(random.choices(l, k=3, weights=[1, 1, 1, 10, 1, 1, 1]))
# ValueError: The number of weights does not match the population_

Chybou je také současné zadání vah a cum_weights.

# print(random.choices(l, k=3, weights=[1, 1, 1, 10, 1], cum_weights=[1, 2, 3, 13, 14]))
# TypeError: Cannot specify both weights and cumulative weights

V ukázkovém kódu jsme zatím jako první argument uvedli seznam, ale totéž platí i pro tuply a řetězce.

Oprava osiva náhodného čísla

Zadáním libovolného celého čísla do funkce seed() modulu random lze stanovit semeno náhodného čísla a inicializovat generátor náhodných čísel.

Po inicializaci stejným semenem se prvky vybírají vždy stejným způsobem.

random.seed(0)
print(random.choice(l))
# 3

random.seed(0)
print(random.choice(l))
# 3