You can not select more than 25 topics Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.
 
 
 
 
 
 

313 lines
7.8 KiB

using System;
using System.Collections;
using System.Collections.Generic;
using Random = System.Random;
namespace ET
{
public class ValleyRandom
{
private Random random = new Random(Guid.NewGuid().GetHashCode());
public void SetSeed(int seed)
{
random = new Random(seed);
}
public ulong RandUInt64()
{
byte[] byte8 = new byte[8];
random.NextBytes(byte8);
return BitConverter.ToUInt64(byte8, 0);
}
public int RandInt32()
{
return random.Next();
}
public uint RandUInt32()
{
return (uint) random.Next();
}
public long RandInt64()
{
byte[] byte8 = new byte[8];
random.NextBytes(byte8);
return BitConverter.ToInt64(byte8, 0);
}
/// <summary>
/// 获取lower与Upper之间的随机数,包含下限,不包含上限
/// </summary>
/// <param name="lower"></param>
/// <param name="upper"></param>
/// <returns></returns>
public int RandomNumber(int lower, int upper)
{
int value = random.Next(lower, upper);
return value;
}
public long NextLong(long minValue, long maxValue)
{
if (minValue > maxValue)
{
throw new ArgumentException("minValue is great than maxValue", "minValue");
}
long num = maxValue - minValue;
return minValue + (long) (random.NextDouble() * num);
}
public bool RandomBool()
{
return random.Next(2) == 0;
}
public T RandomArray<T>(T[] array)
{
return array[RandomNumber(0, array.Length)];
}
public int RandomArray_Len2(int[] array)
{
return RandomHelper.RandomNumber(array[0], array[1]);
}
public T RandomArray<T>(List<T> array)
{
return array[RandomNumber(0, array.Count)];
}
/// <summary>
/// 打乱数组
/// </summary>
/// <typeparam name="T"></typeparam>
/// <param name="arr">要打乱的数组</param>
public void BreakRank<T>(List<T> arr)
{
if (arr == null || arr.Count < 2)
{
return;
}
for (int i = 0; i < arr.Count; i++)
{
int index = random.Next(0, arr.Count);
T temp = arr[index];
arr[index] = arr[i];
arr[i] = temp;
}
}
public int[] GetRandoms(int sum, int min, int max)
{
int[] arr = new int[sum];
int j = 0;
//表示键和值对的集合。
Hashtable hashtable = new Hashtable();
Random rm = random;
while (hashtable.Count < sum)
{
//返回一个min到max之间的随机数
int nValue = rm.Next(min, max);
// 是否包含特定值
if (!hashtable.ContainsValue(nValue))
{
//把键和值添加到hashtable
hashtable.Add(nValue, nValue);
arr[j] = nValue;
j++;
}
}
return arr;
}
/// <summary>
/// 随机从数组中取若干个不重复的元素,
/// 为了降低算法复杂度,所以是伪随机,对随机要求不是非常高的逻辑可以用
/// </summary>
/// <typeparam name="T"></typeparam>
/// <param name="sourceList"></param>
/// <param name="destList"></param>
/// <param name="randCount"></param>
public bool GetRandListByCount<T>(List<T> sourceList, List<T> destList, int randCount)
{
if (sourceList == null || destList == null || randCount < 0)
{
return false;
}
destList.Clear();
if (randCount >= sourceList.Count)
{
foreach (var val in sourceList)
{
destList.Add(val);
}
return true;
}
if (randCount == 0)
{
return true;
}
int beginIndex = random.Next(0, sourceList.Count - 1);
for (int i = beginIndex; i < beginIndex + randCount; i++)
{
destList.Add(sourceList[i % sourceList.Count]);
}
return true;
}
public float RandFloat01()
{
int a = RandomNumber(0, 1000000);
return a / 1000000f;
}
private int Rand(int n)
{
// 注意,返回值是左闭右开,所以maxValue要加1
return random.Next(1, n + 1);
}
/// <summary>
/// 通过权重随机
/// </summary>
/// <param name="weights"></param>
/// <returns></returns>
public int RandomByWeight(int[] weights)
{
int sum = 0;
for (int i = 0; i < weights.Length; i++)
{
sum += weights[i];
}
int number_rand = Rand(sum);
int sum_temp = 0;
for (int i = 0; i < weights.Length; i++)
{
sum_temp += weights[i];
if (number_rand <= sum_temp)
{
return i;
}
}
return -1;
}
public int RandomByWeight(List<int> weights)
{
if (weights.Count == 0)
{
return -1;
}
if (weights.Count == 1)
{
return 0;
}
int sum = 0;
for (int i = 0; i < weights.Count; i++)
{
sum += weights[i];
}
int number_rand = Rand(sum);
int sum_temp = 0;
for (int i = 0; i < weights.Count; i++)
{
sum_temp += weights[i];
if (number_rand <= sum_temp)
{
return i;
}
}
return -1;
}
public int RandomByWeight(List<int> weights, int weightRandomMinVal)
{
if (weights.Count == 0)
{
return -1;
}
if (weights.Count == 1)
{
return 0;
}
int sum = 0;
for (int i = 0; i < weights.Count; i++)
{
sum += weights[i];
}
int number_rand = Rand(Math.Max(sum, weightRandomMinVal));
int sum_temp = 0;
for (int i = 0; i < weights.Count; i++)
{
sum_temp += weights[i];
if (number_rand <= sum_temp)
{
return i;
}
}
return -1;
}
public int RandomByWeight(List<long> weights)
{
if (weights.Count == 0)
{
return -1;
}
if (weights.Count == 1)
{
return 0;
}
long sum = 0;
for (int i = 0; i < weights.Count; i++)
{
sum += weights[i];
}
long number_rand = NextLong(1, sum + 1);
long sum_temp = 0;
for (int i = 0; i < weights.Count; i++)
{
sum_temp += weights[i];
if (number_rand <= sum_temp)
{
return i;
}
}
return -1;
}
}
}