真随机数,随机数辅助类

Posted sanyejun

tags:

篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了真随机数,随机数辅助类相关的知识,希望对你有一定的参考价值。

using System.Collections;
using System.Collections.Generic;
using UnityEngine;
using System;
using System.Linq;

public static class RandomHelper
{
    // 默认生成一个自动分配随机种子的随机数生成器
    private static System.Random globalRandomGenerator = CreateRandom();
    
    /// <summary>
    /// 创建一个新的全局随机数生成器
    /// </summary>
    public static void GenerateNewRandomGenerator()
    {
        globalRandomGenerator = CreateRandom();
    }
    
    /// <summary>
    /// 创建一个新的全局随机数生成器,使用指定的种子初始化此对象
    /// </summary>
    public static void GenerateNewRandomGenerator(int seed)
    {
        globalRandomGenerator = CreateRandom(seed);
    }
    
    /// <summary>
    /// 创建一个产生不重复随机数的随机数生成器实例, 自动分配随机种子
    /// </summary>
    /// <returns></returns>
    private static System.Random CreateRandom()
    {
        long tick = DateTime.Now.Ticks;
        return new System.Random((int)(tick & 0xffffffffL) | (int)(tick >> 32));
    }
    
    /// <summary>
    /// 创建一个产生不重复随机数的随机数生成器实例, 使用指定的种子初始化此对象
    /// </summary>
    /// <returns></returns>
    private static System.Random CreateRandom(int seed)
    {
        return new System.Random(seed);
    }
    
    /// <summary>
    /// 无符号64位整型
    /// </summary>
    /// <returns></returns>
    public static UInt64 RandomUInt64()
    {
        var bytes = new byte[8];
        globalRandomGenerator.NextBytes(bytes);
        return BitConverter.ToUInt64(bytes, 0);
    }
    
    /// <summary>
    /// 有符号64位整型
    /// </summary>
    /// <returns></returns>
    public static Int64 RandomInt64()
    {
        var bytes = new byte[8];
        globalRandomGenerator.NextBytes(bytes);
        return BitConverter.ToInt64(bytes, 0);
    }
    
    /// <summary>
    /// 具有最大范围的随机正整型
    /// </summary>
    /// <param name="max"></param>
    /// <returns></returns>
    public static int RandomNumber(int max)
    {
        int value = globalRandomGenerator.Next(0, max);
        return value;
    }
    
    /// <summary>
    /// 指定范围内的随机整型
    /// </summary>
    /// <param name="lower">返回的随机数的下界(包含)</param>
    /// <param name="upper">返回的随机数的上界(不包含)</param>
    /// <returns></returns>
    public static int RandomNumber(int lower, int upper)
    {
        int value = globalRandomGenerator.Next(lower, upper);
        return value;
    }
    
    /// <summary>
    /// [0.0-1.0)范围内的随机浮点数。
    /// 返回一个大于或等于 0.0 且小于 1.0 的随机浮点数。
    /// </summary>
    /// <returns></returns>
    public static float RandomFloat01()
    {
        return (float)globalRandomGenerator.NextDouble();
    }
    
    /// <summary>
    /// 随机浮点数
    /// </summary>
    /// <returns></returns>
    public static float RandomFloat()
    {
        return RandomInt64() * RandomFloat01();
    }
    
    /// <summary>
    /// 具有最大范围的随机正浮点数
    /// </summary>
    /// <param name="max"></param>
    /// <returns></returns>
    public static float RandomFloat(float max)
    {
        return (float)globalRandomGenerator.NextDouble() * max;
    }
    
    /// <summary>
    /// 指定范围内的随机浮点数
    /// </summary>
    /// <param name="min"></param>
    /// <param name="max"></param>
    /// <returns></returns>
    public static float RandomFloat(float min, float max)
    {
        if (min < max)
            return (float)globalRandomGenerator.NextDouble() * (max - min) + min;
        else
            return max;
    }
    
    /// <summary>
    /// 随机三维单位向量/单位球体内的随机坐标点
    /// </summary>
    /// <returns></returns>
    public static Vector3 RandomNormalizedVector3()
    {
        return new Vector3(RandomInt64(),RandomInt64(),RandomInt64()).normalized;
    }
    
    /// <summary>
    /// 随机三维向量
    /// </summary>
    /// <returns></returns>
    public static Vector3 RandomVector3()
    {
        return new Vector3(RandomFloat(),RandomFloat(),RandomFloat());
    }
    
    /// <summary>
    /// 具有最大范围的随机三维向量/顶点在原点的长方体内的随机坐标点
    /// </summary>
    /// <param name="xMax">返回的随机数的上界(不包含)</param>
    /// <param name="yMax">返回的随机数的上界(不包含)</param>
    /// <param name="zMax">返回的随机数的上界(不包含)</param>
    /// <returns></returns>
    public static Vector3 RandomVector3(float xMax, float yMax = 0, float zMax = 0)
    {
        return new Vector3(RandomFloat(xMax), RandomFloat(yMax), RandomFloat(zMax));
    }
    
    /// <summary>
    /// 指定范围的三维向量/长方体内的随机坐标点
    /// </summary>
    /// <param name="xMin">返回的随机数的下界(包含)</param>
    /// <param name="xMax">返回的随机数的上界(不包含)</param>
    /// <param name="yMin">返回的随机数的下界(包含)</param>
    /// <param name="yMax">返回的随机数的上界(不包含)</param>
    /// <param name="zMin">返回的随机数的下界(包含)</param>
    /// <param name="zMax">返回的随机数的上界(不包含)</param>
    /// <returns></returns>
    public static Vector3 RandomVector3(float xMin, float xMax, float yMin, float yMax, float zMin, float zMax)
    {
        return new Vector3(RandomFloat(xMin, xMax),RandomFloat(yMin, yMax),RandomFloat(zMin, zMax));    
    }
    
    /// <summary>
    /// 随机二维向量
    /// </summary>
    /// <returns></returns>
    public static Vector2 RandomVector2()
    {
        return new Vector2(RandomFloat(),RandomFloat());
    }
    
    /// <summary>
    /// 具有最大范围的随机二维向量
    /// </summary>
    /// <param name="xMax">返回的随机数的上界(不包含)</param>
    /// <param name="yMax">返回的随机数的上界(不包含)</param>
    /// <returns></returns>
    public static Vector2 RandomVector2(float xMax, float yMax = 0)
    {
        return new Vector2(RandomFloat(xMax), RandomFloat(yMax));
    }
    
    /// <summary>
    /// 指定范围的随机二维向量
    /// </summary>
    /// <param name="xMin"></param>
    /// <param name="xMax"></param>
    /// <param name="yMin"></param>
    /// <param name="yMax"></param>
    /// <returns></returns>
    public static Vector2 RandomVector2(float xMin, float xMax, float yMin, float yMax)
    {
        return new Vector2(RandomFloat(xMin, xMax),RandomFloat(yMin, yMax));
            
    }
    
    /// <summary>
    /// 返回圆圈范围内的随机坐标点
    /// </summary>
    /// <param name="range"></param>
    /// <param name="y"></param>
    /// <returns></returns>
    public static Vector3 RandomVector3InRangeCircle(float range, float y = 0)
    {
        float length = RandomFloat(0, range);
        float angle = RandomFloat(0, 360);
        return new Vector3(
            (float)(length * Math.Sin(angle * (Math.PI / 180))),
            y, 
            (float)(length * Math.Cos(angle * (Math.PI / 180)))
        );
    }
    
    /// <summary>
    /// 随机布尔值
    /// </summary>
    /// <returns></returns>
    public static bool RandomBoolean()
    {
        if (globalRandomGenerator.Next() % 2 == 0)
            return false;
        return true;
    }
    
    /// <summary>
    /// 测试随机事件在一次独立实验中是否发生
    /// </summary>
    /// <param name="probability"> [0f, 1f] 范围的概率 </param>
    /// <returns> 如果事件发生返回 true, 否则返回 false </returns>
    public static bool Test(float probability)
    {
        return RandomFloat01() < probability;
    }

    /// <summary>
    /// 产生正态分布的随机数
    /// 正态分布随机数落在 μ±σ, μ±2σ, μ±3σ 的概率依次为 68.26%, 95.44%, 99.74%
    /// </summary>
    /// <param name="averageValue"> 正态分布的平均值, 即 N(μ, σ^2) 中的 μ </param>
    /// <param name="standardDeviation"> 正态分布的标准差, 即 N(μ, σ^2) 中的 σ </param>
    /// <returns> 返回正态分布的随机数. 理论值域是 μ±∞ </returns>
    public static float Normal(float averageValue, float standardDeviation)
    {
        //
        // https://en.wikipedia.org/wiki/Box-Muller_transform
        //
        return averageValue + standardDeviation * (float)
        (
            Math.Sqrt(-2 * Math.Log(1 - RandomFloat01())) * Math.Sin(Math.PI *2 * RandomFloat01())
        );
    }
    
    /// <summary>
    /// 随机获取List中的一个元素
    /// </summary>
    /// <param name="list"></param>
    /// <typeparam name="T"></typeparam>
    /// <returns></returns>
    public static T Choice<T>(List<T> list)
    {
        if (list.Count == 0)
        {
            return default(T);
        }

        int index = RandomNumber(0, list.Count);
        return list[index];
    }
    
    /// <summary>
    /// 随机获取Dictionary中的一个元素
    /// </summary>
    /// <param name="dict"></param>
    /// <typeparam name="K"></typeparam>
    /// <typeparam name="T"></typeparam>
    /// <returns></returns>
    public static T Choice<K,T>(Dictionary<K,T> dict)
    {
        if (dict.Count == 0)
        {
            return default(T);
        }

        int index = RandomNumber(0, dict.Count);
        return dict.Values.ToArray()[index];
    }
    
    /// <summary>
    /// 随机颜色
    /// </summary>
    /// <returns></returns>
    public static Color RandomColor()
    {
        Byte[] temp = new Byte[4];
        globalRandomGenerator.NextBytes(temp);
        return new Color(temp[0], temp[1], temp[2], temp[3]);
    }
    
    public static Color RandomColor(int alpha)
    {
        Byte[] temp = new Byte[3];
        globalRandomGenerator.NextBytes(temp);

        if (alpha < 0)
            alpha = 0;
        if (alpha > 255)
            alpha = 255;

        return new Color(temp[0], temp[1], temp[2], alpha);
    }
}

 

以上是关于真随机数,随机数辅助类的主要内容,如果未能解决你的问题,请参考以下文章

区块链技术硬核产品——HPB芯链硬件真随机数

强!真不愧是人类高质量男性!仅用三行代码就从一千个数字随机选出了一百个不同的数字!

强!真不愧是人类高质量男性!仅用三行代码就从一千个数字随机选出了一百个不同的数字!

强!真不愧是人类高质量男性!仅用三行代码就从一千个数字随机选出了一百个不同的数字!

真随机数生成器 (TRNG)、Haskell 和经验/形式方法

Linux真随机数的生成