2014-09-27 4 views
1

Есть ли более или менее стандартное решение для создания идентичных рядов псевдослучайных целых чисел в Clojure?Как создать идентичную последовательность псевдослучайных целых чисел?

Я знаю три стандартных функции для рандомизации: rand, rand-int и rand-nth, но они, похоже, не предоставляют никакого способа «установить» их внутреннее состояние.

+0

возможный дубликат [Как генерируются воспроизводимые случайные последовательности с рандов -int] (http://stackoverflow.com/questions/24007063/how-to-generated-repeatable-random-sequences-with-rand-int) – jonrsharpe

+0

Возможный дубликат [Почему не многократно генерирует воспроизводимые случайные числа при использовании семя в Clojure?] (http://stackoverflow.com/questions/22441860/why-doesnt-repeatedly-generate-reproducible-random-numbers-when-using-a-seed-in) – jbr

+0

@jonrsharpe, действительно кажется быть дубликатом, но цитируемый вопрос все равно не имеет достойного ответа. – Mark

ответ

4
(defn randomish [seed] 
    (repeatedly 
    (let [gen (java.util.Random. seed)] 
     (fn [] (.nextInt gen))))) 

(take 5 (randomish 10)) 
;(-1157793070 1913984760 1107254586 1773446580 254270492) 

(take 5 (randomish 10)) 
;(-1157793070 1913984760 1107254586 1773446580 254270492) 

В randomish, repeatedly

  • захватывает функцию
  • , который захватывает Random объекта
  • , который удерживает изменяемое внутреннее состояние
  • инициированного seed.

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

(Если вы ошиблись, , пожалуйста,. Исправьте меня. possible duplicate, похоже, делает тяжелый ход).

Примечание

Это может быть лучше, в Clojure, чтобы позвонить .nextLong вместо nextInt.


По желанию, адаптированный для борьбы с опциональным (эксклюзивный) предел:

(defn randomish 
    ([seed] 
    (repeatedly 
     (let [gen (java.util.Random. seed)] 
     (fn [] (.nextInt gen))))) 
    ([seed limit] 
    (repeatedly 
     (let [gen (java.util.Random. seed)] 
     (fn [] (.nextInt gen limit)))))) 

... производство

(take 5 (randomish 10 100)) 
;(13 80 93 90 46) 

(take 5 (randomish 10 100)) 
;(13 80 93 90 46) 
+0

Отличный ответ, спасибо! – Mark

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