2009-06-24 2 views
0

Использование PHP (приветствуются другие языки, используя общедоступные встроенные модули), как я могу получить случайное (или псевдослучайное) число, которое НЕ соответствует определенные критерии?Получить случайное число, которое не соответствует критериям (PHP)

IE: Я хочу $x = rand(0, 99), но только если ($x % 9) != 0.

Что такое чистый приемлемый способ сдерживания случайных чисел по таким критериям?

В качестве примера, используя while() петлю, и, возможно, break ИНГ, когда у нас есть то, что соответствует нашим критериям, то, используя случайное число после цикла ?:

while (($rand_key = array_rand($array_of_items)) && ($rand_key % 9 == 0)) 
{ 
    // Do nothing? 
} 

Или что-то вроде:

while ($rand_key = array_rand($array_of_items)) 
{ 
    if ($rand_key % 9 == 0) { 
     break; 
    } 
} 

Или есть более краткий или подходящий способ для этого?

+0

Обратите внимание, что ваш второй пример должен прорваться!= вместо == – schnaader

ответ

3

Один из редких случаев, когда цикл делать-то время на самом деле помогает

$testData = array(7, 8, 9); 

do { 
    $rand = array_rand($testData); 
} while ($testData[$rand] % 9 == 0); 

echo $testData[$rand]; 
+0

+1 - Идеально подходит для такого типа сценариев. (Попытайтесь, проверьте, повторите попытку неудачи.) –

+2

Do ... Пока слышит его имя и его уши. Меня!? Кто-то хочет меня использовать! – Travis

4

Это ваш точный пример использования или просто пример?

Если вы пытаетесь (в частности) получить числа от 0 до 99, исключая точные кратные 9, я могу подумать о нескольких путях, чтобы избежать неуклюжий цикл. Людям не нравится цикл, генерируя случайные числа, потому что вы можете зацикливаться навсегда. (Но, конечно, не произойдет, если вы не чрезвычайно повезло тип -. Такой человек, который, случается, чтобы получить себя в перестрелках с Клинтом Иствудом в спагетти-вестернах)

  1. Вы могли бы поиск таблицу, которая переназначает случайные числа, которые вы получаете в те, которые вы хотите.

  2. Производите 0-88 случайным образом. Умножьте результат на 9 и разделите его на 8 и получите целочисленный результат (этаж, а не раунд). Затем добавьте 1.

Оба они имеют предсказуемое время.

+0

if ($ rand% 9 == 0) $ rand ++; // :-) –

+0

@ Csaba - Я сделал это несколько раз. Но он работает только в том случае, если вы не заботитесь о распределении чисел. – Nosredna

0

Это соответствует 'сжатое' требование:

while(($x = rand(0, 99)) % 9 == 0); 
echo $x; 

или

while ($array_of_items[$rand_key = array_rand($array_of_items)] % 9 == 0); 
echo $array_of_items[$rand_key];  

Однако, это не очень читабельна.

1

Альтернативный метод, который торгует местами, потенциально, несколькими вызовами PRNG, для случаев с небольшим количеством допустимых результатов (как в вашем примере) будет заполнять массив действительными решениями и использовать PRNG для создания индекс в массив.

Какой бы метод вы ни выбрали, я бы также предложил для производственного кода указать причину ограничения соответствующим и доступным способом.

+1

Я абсолютно согласен с замечанием каких-либо странных аргументов в документации. Если вы не ссылались на мои примеры кода, которые были только примерами. Спасибо за Ваш ответ. –

Смежные вопросы