Co robi np.random.seed
poniższy kod z samouczka Scikit-Learn? Nie znam się zbyt dobrze na generatorach losowych stanów NumPy, więc naprawdę doceniłbym wyjaśnienie tego dla laika.
np.random.seed(0)
indices = np.random.permutation(len(iris_X))
np.random.seed(0)
sprawia, że liczby losowe są przewidywalne
>>> numpy.random.seed(0) ; numpy.random.rand(4)
array([ 0.55, 0.72, 0.6 , 0.54])
>>> numpy.random.seed(0) ; numpy.random.rand(4)
array([ 0.55, 0.72, 0.6 , 0.54])
Z resetem nasion (za każdym razem), to samo każdym razem pojawia się zestaw liczb.
Jeśli losowe ziarno nie zostanie zresetowane, przy każdym wywołaniu pojawiają się różne liczby:
>>> numpy.random.rand(4)
array([ 0.42, 0.65, 0.44, 0.89])
>>> numpy.random.rand(4)
array([ 0.96, 0.38, 0.79, 0.53])
Liczby (pseudo-) losowe działają zaczynając od liczby (nasienia), mnożąc ją przez dużą liczbę, dodając przesunięcie, a następnie biorąc modulo tej sumy. Wynikowa liczba jest następnie używana jako ziarno do wygenerowania następnej „losowej” liczby. Kiedy ustawiasz ziarno (za każdym razem), robi to samo za każdym razem, dając ci te same liczby.
Jeśli chcesz pozornie losowe liczby, nie ustawiaj nasion. Jeśli masz kod, który używa liczb losowych, które chcesz debugować, bardzo pomocne może być ustawienie zarodka przed każdym uruchomieniem, aby kod działał tak samo przy każdym uruchomieniu.
Aby uzyskać najbardziej losowe numery dla każdego biegu, zadzwoń numpy.random.seed()
. Spowoduje to, że numpy ustawi ziarno na losową liczbę uzyskaną z/dev/urandom
jego analogu Windows lub, jeśli żaden z nich nie jest dostępny, użyje zegara.
Aby uzyskać więcej informacji na temat używania nasion do generowania liczb pseudolosowych, zobacz wikipedia .
numpy.random.seed(None)
, „spróbuje odczytać dane z / dev / urandom (lub analogu Windows), jeśli są dostępne, lub w przeciwnym razie zaczną od początku”.numpy.random.seed(None)
. Zaktualizowałem odpowiedź o te informacje i link do dokumentów.seed
kompatybilnymi.Jeśli ustawisz za
np.random.seed(a_fixed_number)
każdym razem, gdy wywołasz inną losową funkcję numpy, wynik będzie taki sam:Jeśli jednak zadzwonisz raz i użyjesz różnych losowych funkcji, wyniki będą nadal różne:
źródło
np.random
wywołań, dopóki ziarno nie zostanie zmienione? Konieczność nazywania go za każdym razem wydaje się niepotrzebnie pełna i łatwa do zapomnienia.def seed_first(fun, seed=0):
|\tdef wrapped(*args, **kwargs):
|\t\tnp.random.seed(seed)
|\t\treturn fun(*args, **kwargs)
|\treturn wrapped
, a następniefor m in np.random.__all__:
|\tif m != 'seed':
|\t\tsetattr(np.random, m, seed_first(getattr(np.random, m)))
Może to jednak prowadzić do bardzo subtelnych błędów i dziwnych zachowań na dłuższą metę. (Zamień \ t na cztery spacje, a | na podziały linii ...)np.random.seed()
raz na początku programu zawsze da ten sam wynik dla tego samego ziarna, ponieważ kolejne wywołanianp.random
funkcji będą deterministycznie zmieniać ziarno dla kolejnych wywołań. Wywołanienp.random.seed()
przed każdym wywołaniemnp.random
funkcji prawdopodobnie przyniesie niepożądane rezultaty.Jak wspomniano, numpy.random.seed (0) ustawia losowe ziarno na 0, więc pseudolosowe liczby, które otrzymujesz z losowych, zaczną się od tego samego punktu. W niektórych przypadkach może to być przydatne do debugowania. JEDNAK po pewnym przeczytaniu wydaje się to niewłaściwa metoda, jeśli masz wątki, ponieważ nie jest to bezpieczne.
z różnic między numpy-random-and-random-random-in-python :
przykład jak to zrobić:
może dać:
Na koniec zauważ, że mogą wystąpić przypadki, w których inicjowanie na 0 (w przeciwieństwie do zarodka, który nie ma wszystkich bitów 0) może spowodować nierównomierne rozkłady dla kilku pierwszych iteracji ze względu na sposób działania xor, ale zależy to od algorytmu i jest poza moimi obecnymi obawami i zakresem tego pytania.
źródło
Używałem tego bardzo często w sieciach neuronowych. Powszechnie wiadomo, że kiedy rozpoczynamy trening sieci neuronowej, losowo inicjujemy wagi. Model jest szkolony w zakresie tych wag w określonym zestawie danych. Po kilku epokach otrzymasz wyszkolony zestaw ciężarów.
Załóżmy teraz, że chcesz ponownie ćwiczyć od zera lub przekazać model innym osobom w celu odtworzenia wyników, wagi zostaną ponownie zainicjalizowane na liczby losowe, które w większości będą inne niż wcześniejsze. Uzyskane wyćwiczone wagi po tej samej liczbie epok (przy zachowaniu tych samych danych i innych parametrów), jak wcześniej, będą się różnić. Problem polega na tym, że model nie jest już odtwarzalny, ponieważ za każdym razem, gdy trenujesz swój model od zera, zapewnia on różne zestawy wag. Wynika to z faktu, że model jest inicjowany za każdym razem różnymi liczbami losowymi.
Co jeśli za każdym razem, gdy zaczynasz trening od zera, model jest inicjowany do tego samego zestawu losowych ciężarów inicjalizacyjnych? W takim przypadku Twój model może stać się odtwarzalny. Osiąga się to przez numpy.random.seed (0). Wspominając seed () o określonej liczbie, zawsze trzymasz się tego samego zestawu liczb losowych.
źródło
Wyobraź sobie, że pokazujesz komuś, jak zakodować coś za pomocą kilku „losowych” liczb. Używając numpy seed, mogą użyć tego samego numeru nasion i uzyskać ten sam zestaw liczb „losowych”.
Nie jest to więc przypadkowe, ponieważ algorytm wyrzuca liczby, ale wygląda jak losowo wygenerowana wiązka.
źródło
Losowe ziarno określa punkt początkowy, kiedy komputer generuje losową sekwencję liczb.
Załóżmy na przykład, że chcesz wygenerować liczbę losową w programie Excel (uwaga: program Excel ustawia limit 9999 dla zarodka). Jeśli wpiszesz liczbę w polu Losowe ziarno podczas procesu, będziesz mógł ponownie użyć tego samego zestawu liczb losowych. Jeśli wpiszesz „77” w polu i wpiszesz „77” przy następnym uruchomieniu generatora liczb losowych, Excel wyświetli ten sam zestaw liczb losowych. Jeśli wpiszesz „99”, otrzymasz zupełnie inny zestaw liczb. Ale jeśli wrócisz do zera 77, otrzymasz ten sam zestaw liczb losowych, od którego zacząłeś.
Na przykład: „weź liczbę x, dodaj 900 + x, a następnie odejmij 52”. Aby proces się rozpoczął, musisz podać liczbę początkową x (ziarno). Weźmy liczbę początkową 77:
Dodaj 900 + 77 = 977 Odejmij 52 = 925 Zgodnie z tym samym algorytmem druga „losowa” liczba to:
900 + 925 = 1825 Odejmij 52 = 1773 Ten prosty przykład jest wzorcem, ale algorytmy generowania liczb komputerowych są znacznie bardziej skomplikowane
źródło
Wszystkie liczby losowe wygenerowane po ustawieniu określonej wartości początkowej są takie same na wszystkich platformach / systemach.
źródło
W dokumentach Numpy znajduje się ładne wyjaśnienie: https://docs.scipy.org/doc/numpy-1.15.1/reference/generated/numpy.random.RandomState.html odnosi się do generatora liczb pseudolosowych Mersenne Twister . Więcej szczegółów na temat algorytmu tutaj: https://en.wikipedia.org/wiki/Mersenne_Twister
źródło
Daje to następujący wynik:
array([5, 0, 3, 3, 7])
Ponownie, jeśli uruchomimy ten sam kod, otrzymamy ten sam wynik.Teraz, jeśli zmienimy wartość początkową 0 na 1 lub inne:
Daje to następujące dane wyjściowe:
array([5 8 9 5 0])
ale teraz dane wyjściowe nie są takie same jak powyżej.źródło
Wszystkie powyższe odpowiedzi pokazują wdrożenie
np.random.seed()
kodu. Postaram się jak najlepiej wyjaśnić, dlaczego tak się dzieje. Komputery to maszyny zaprojektowane w oparciu o predefiniowane algorytmy. Każde wyjście z komputera jest wynikiem algorytmu zaimplementowanego na wejściu. Kiedy więc poprosimy komputer o generowanie liczb losowych, upewnij się, że są one losowe, ale komputer nie wymyślił ich losowo!Kiedy więc piszemy,
np.random.seed(any_number_here)
algorytm wyświetli określony zestaw liczb, który jest unikalny dla argumentuany_number_here
. To prawie tak, jakby konkretny zestaw liczb losowych można uzyskać, jeśli przekażemy poprawny argument. Będzie to jednak wymagało od nas znajomości działania algorytmu, co jest dość uciążliwe.Na przykład, jeśli napiszę
np.random.seed(10)
konkretny zestaw liczb, które otrzymam, pozostaną takie same, nawet jeśli wykonam tę samą linię po 10 latach, chyba że algorytm się zmieni.źródło