Pomoc - Szukaj - Użytkownicy - Kalendarz
Pełna wersja: [PHP]Funkcja losująca, losowanie wielokrotne
Forum PHP.pl > Forum > Przedszkole
jam09
Hej
Proszę o pomoc, chciałbym wylosować 10 liczb ze 100. Mógłbym użyć funkcji rand(), ale czasami zdarzają się powtórzenia liczb np. 10 i 10. Jak mógłbym uniknąć powtórzeń ? Z góry dzięki za pomoc.
Daiquiri
Jeżeli chcesz korzystać z rand() to postaw warunek if(wylosowana liczba == poprzednia liczba) losuj jeszcze raz.
toaspzoo
jeżeli chodzi o niepowtarzający się, to użyj md5(microtime)
jam09
Jeśli jest inna metoda niż rand() to z chęcią bym skorzystał.
Daiquiri
Jak sobie wyobrażasz 10 liczb porównywać ? Każdą liczbę trzeba sprawdzić przez 9 liczb. To będzie 90 if. Jak dla mnie straszne opóźnienie. Zresztą skąd mam mieć pewność że nie wylosuje znowu liczby, która była już wylosowana ? Można by było puścić to jeszcze raz, a potem jeszcze raz, aż do skutku ale ile zajmie to czasu ? Nie ma czegoś czym by było lepiej i szybciej ?
Crozin
Jaka jest maksymalna pula? Jeżeli jest to 100, 1 000 czy 10 000 możesz najpierw wygenerować sobie te wszystkie elementy po czym z nich wylosować 10:
  1. $range = range(1, 10000);
  2. $items = array_rand($range, 10);
Możesz też po prostu losować liczbę i sprawdzać czy takowa nie została już wylosowana:
  1. $items = array();
  2.  
  3. do {
  4. $rand = mt_rand(0, 10000);
  5. if (!in_array($rand, $items)) {
  6. $items[] = $rand;
  7. }
  8. } while (count($items) < 10);
Sposobów jest cała masa...
Daiquiri
No co Ty - porównujesz 10 zmiennych nie 90 smile.gif. Sposobów jest multum, możesz np. wykorzystać tablice.
phpion
@Crozin:
Mam lekkiego bzika na punkcie Nesquika i optymalizacji wydajności kodów, więc pozwolę sobie nieco zmodyfikować Twój kod. Lepiej zamiast in_array() skorzystać z isset() i nieco zmienić sposób przechowywania wylosowanych liczb.
  1. $items = array();
  2.  
  3. do {
  4. $rand = mt_rand(0, 10000);
  5. //if (!in_array($rand, $items)) {
  6. if (!isset($items[$rand])) {
  7. //$items[] = $rand;
  8. $items[$rand] = TRUE;
  9. }
  10. } while (count($items) < 10);

Wypadałoby jeszcze pozbyć się tego count'a na rzecz zwykłego licznika, ale to już pozostawiam autorowi wątku w ramach treningu smile.gif
Crozin
Wiem, że ideone.com to nie najlepsza platforma do testów, ale... http://ideone.com/hN2J6 Oczywiście masz rację - odpowiednio dostosowane Twoje rozwiązanie jest bezsprzecznie szybsze. Ale na dobrą sprawę zyskujemy te 0,000004 sekundy (w przypadku normalnej platformy wyszłoby pewnie jeszcze mniej) kosztem gorszego kodu (bo jest mniej oczywisty itd.).

Czy warto? W normalnym przypadku nie.
To jest wersja lo-fi głównej zawartości. Aby zobaczyć pełną wersję z większą zawartością, obrazkami i formatowaniem proszę kliknij tutaj.
Invision Power Board © 2001-2025 Invision Power Services, Inc.