コード例 #1
0
        // Fisher-Yates shuffle, shuffling an array of 32-bit values, use the provided key.
        public static void Xorshift128plusShuffle32(ref Xorshift128PlusKey key, uint32[] storage)
        {
            uint32 i = 0;
            uint32 nextpos1 = 0, nextpos2 = 0;

            for (i = (uint32)storage.Length; i > 2; i -= 2)
            {
                Xorshift128Plus_bounded_two_by_two(ref key, i, i - 1, ref nextpos1, ref nextpos2);

                uint32 tmp1 = storage[i - 1];       // Probably in cache
                uint32 val1 = storage[nextpos1];
                storage[i - 1]    = val1;
                storage[nextpos1] = tmp1;
                uint32 tmp2 = storage[i - 2];       // Probably in cache
                uint32 val2 = storage[nextpos2];
                storage[i - 2]    = val2;
                storage[nextpos2] = tmp2;
            }
            if (i > 1)
            {
                uint32 nextpos = Xorshift128Plus_bounded(ref key, i);
                uint32 tmp     = storage[i - 1];    // Probably in cache
                uint32 val     = storage[nextpos];
                storage[i - 1]   = val;
                storage[nextpos] = tmp;
            }
        }
コード例 #2
0
        // Returns a new 64-bit random number.
        public static uint64 Xorshift128Plus(ref Xorshift128PlusKey nextKey)
        {
            uint64 s1 = nextKey.s1;
            uint64 s0 = nextKey.s2;

            nextKey.s1 = s0;
            s1        ^= s1 << 23;                         // a
            nextKey.s2 = s1 ^ s0 ^ (s1 >> 18) ^ (s0 >> 5); // b, c
            return(nextKey.s2 + s0);
        }
コード例 #3
0
        private static void Xorshift128Plus_bounded_two_by_two(
            ref Xorshift128PlusKey key,
            uint32 bound1, uint32 bound2,
            ref uint32 bounded1, ref uint32 bounded2
            )
        {
            uint64 rand = Xorshift128Plus(ref key);

            bounded1 = (uint32)((((rand & 0xFFFFFFFF) * bound1)) >> 32);
            bounded2 = (uint32)(((rand >> 32) * bound2) >> 32);
        }
コード例 #4
0
        // Equivalent to skipping 2^64 xorshift128plus() calls
        // useful to generate a new key from an existing one (multi-threaded context).
        public static void XorshiftPlusJump(ref Xorshift128PlusKey key)
        {
            uint64 s0 = 0;
            uint64 s1 = 0;

            for (uint32 i = 0; i < JumpTable.Length; i++)
            {
                for (int b = 0; b < 64; b++)
                {
                    if ((JumpTable[i] & 1UL) << b != 0)
                    {
                        s0 ^= key.s1;
                        s1 ^= key.s2;
                    }

                    Xorshift128Plus(ref key);
                }
            }

            key.s1 = s0;
            key.s2 = s1;
        }
コード例 #5
0
        static uint32 Xorshift128Plus_bounded(ref Xorshift128PlusKey key, uint32 bound)
        {
            uint64 rand = Xorshift128Plus(ref key);

            return((uint32)(((rand & (0xFFFFFFFF)) * bound) >> 32));
        }