diff options
author | Jesusaves <cpntb1@ymail.com> | 2023-07-13 14:02:13 -0300 |
---|---|---|
committer | Jesusaves <cpntb1@ymail.com> | 2023-07-13 14:02:13 -0300 |
commit | 753f10f92a09c8705d6c294f59b46071890bc4c0 (patch) | |
tree | 1ba5c0a098d368a981f929f52c91a4da411dd318 | |
parent | de036392ae101bff4db9ff4bd7a3bd287ebeb68a (diff) | |
download | serverdata-753f10f92a09c8705d6c294f59b46071890bc4c0.tar.gz serverdata-753f10f92a09c8705d6c294f59b46071890bc4c0.tar.bz2 serverdata-753f10f92a09c8705d6c294f59b46071890bc4c0.tar.xz serverdata-753f10f92a09c8705d6c294f59b46071890bc4c0.zip |
Backport Miller Shuffler Algorithm from TMW Crossroads.
(C) Copyright 2022 Ronald R. Miller, licensed under Apache 2.0 License
-rw-r--r-- | npc/functions/main.txt | 28 |
1 files changed, 28 insertions, 0 deletions
diff --git a/npc/functions/main.txt b/npc/functions/main.txt index a099916f6..f90c99a8b 100644 --- a/npc/functions/main.txt +++ b/npc/functions/main.txt @@ -299,6 +299,34 @@ function script any_of { return getelementofarray(getarg(0), getarrayindex(getarg(0)) + rand2(getarraysize(getarg(0)) - getarrayindex(getarg(0)))); } +// Miller Algorithm implementation for shuffling (PRIG) +// miller_rand( state, seed, array_size ) +function script miller_rand { + .@inx = getarg(0); + .@shuffleID = getarg(1); + .@listSize = getarg(2); + + .@shuffleID += 131 * (.@inx/.@listSize); // have inx overflow effect the mix + .@si = (.@inx + .@shuffleID) % .@listSize; // cut the deck + .@topEven = .@listSize - (.@listSize & 1); // compute reference value + .@r1 = .@shuffleID % 0xFFF; // improved randomizing values + .@r2 = .@shuffleID % 0x3FFF ^ .@r1; + .@r3 = .@shuffleID / 881 + 3; + .@rx = (.@shuffleID / .@listSize) % .@listSize + 1; + + // NOTE: the next line operates only 1/3 the time, the following line 1/2 + // spin multiples of 3 + if (.@si % 3 == 0) .@si = (((.@si/3)*3343+.@r1) % ((.@listSize+2)/3)) * 3; + // reverse+rotate flow of odd #s + if (.@si&1) .@si = (2 * .@r2 + .@topEven - .@si) % .@topEven; + // flip some bits with Xor + if ((.@si ^ .@rx) < .@listSize) .@si ^= .@rx; + // turn more prime wheels + .@si = (.@si * 9973 + .@r3) % .@listSize; + + return .@si; +} + function script die { if ($HARDCORE) { @grace=true; |