1 streams addPrototype: #RandomStream derivedFrom: {PositionableReadStream}.
2 "Answers a series of pseudo-random positive SmallIntegers across the entire
3 value range. It is very fast and has an extremely long period (2^19937-1).
4 Based off the Mersenne Twister code in C at:
5 http://www.math.keio.ac.jp/~matumoto/emt.html"
6 RandomStream addSlot: #state valued: (Array newSize: 624).
7 "This array is used for the calculations and works as a kind of history buffer.
8 The particular size of the array corresponds to / is determined by the
9 desired range of the outputs. See the website for particulars when porting."
11 rs@(RandomStream traits) collectionType
16 rs@(RandomStream traits) newSeed: seed
17 [(rs clone `setting: #{#state. #readLimit}
18 to: {rs state newSameSize. rs state size}) `>> [seed := seed. ]].
20 rs@(RandomStream traits) new
21 [rs newSeed: lobby ticksSinceEpoch].
23 rs@(RandomStream traits) next
25 (pos := rs position) >= rs readLimit ifTrue:
28 rs position := pos + 1.
29 (tmp := rs state at: pos)
33 (((tmp bitShift: 7) bitAnd: 16r9D2C5680)
35 (((tmp bitShift: 15) bitAnd: 16rEFC60000)
37 (tmp bitShift: -18))))
40 rs@(RandomStream traits) seed: seed
43 seed := seed bitAnd: 16rFFFFFFFF.
45 1 below: state size do:
47 seed := 69069 * seed bitAnd: 16rFFFFFFFF.
48 state at: index := seed].
49 rs position := rs readLimit
52 rs@(RandomStream traits) refill
55 0 below: state size - 397
58 ((state at: index) bitAnd: 16r80000000)
60 ((state at: index + 1) bitAnd: 16r7FFFFFFF).
62 (state at: index + 397)
66 ((16r100000000 - (tmp bitAnd: 1)) bitAnd: 16r9908B0DF))].
67 state size - 397 below: state size - 1 do:
70 ((state at: index) bitAnd: 16r80000000)
72 ((state at: index + 1) bitAnd: 16r7FFFFFFF).
74 (state at: index + 397 - state size)
78 ((16r100000000 - (tmp bitAnd: 1)) bitAnd: 16r9908B0DF))].
80 ((state at: 0) bitAnd: 16r80000000)
82 ((state at: 1) bitAnd: 16r7FFFFFFF).
83 state at: state size - 1 :=
88 ((16r100000000 - (tmp bitAnd: 1)) bitAnd: 16r9908B0DF)).
92 SmallInteger traits addImmutableSlot: #Randomizer valued:
93 (RandomStream newSeed: Cloneable clone hash).
94 "TODO: seed with an actual random source, e.g. time values."
95 "TODO: make this non-global and yet persistable."
97 i@(SmallInteger traits) atRandom
99 i Randomizer next mod: i
102 i@(Integer traits) atRandom