private uint NextUInt32(uint maxValue) { if (maxValue == 0) { return(0); } // determine the position of MSB uint mask; if (maxValue == this.cachedMaxValue) { mask = this.cachedValueMask; } else { this.cachedMaxValue = maxValue; mask = this.cachedValueMask = BitScanner.Mask(maxValue - 1); } // uint num; do { num = this.NextUInt32(); num &= mask; } while (num >= maxValue); return(num); }
private static double FullPrecisionDouble_c0o1(Random rng, byte[] buffer) { const int EffectiveBits = BUFFER_SIZE * 8; // exponent var e = -1; do { rng.NextBytes(buffer); var r = BitConverter.ToUInt64(buffer, 0); var ntz = BitScanner.NumberOfTrailingZeros64(r); if (ntz < EffectiveBits) { e -= ntz; break; } e -= EffectiveBits; } while (e > -1024); // if (e <= -1024) { return(0); } // fraction rng.NextBytes(buffer); var f = (long)(BitConverter.ToUInt64(buffer, 0) >> 12); // IEEE-754 return(BitConverter.Int64BitsToDouble(((long)(e + 1023) << 52) | f)); }