自定义随机权重,获取随机数
public class NewBehaviourScript : MonoBehaviour
{
[System.Serializable]
public class RandomConfig
{
public RandomConfig(int v,int w)
{
value = v;
weight = w;
}
//返回值(不一定是int,float、枚举、类、结构体都可以)
public int value;
//随机权重
public int weight;
}
[SerializeField] private List<RandomConfig> randomConfigList = new List<RandomConfig>();
//---------
private RandomConfig GetRandomValue()
{
//累加结算总权重
int totalWeight = randomConfigList.Aggregate(0,(all,next) => all += next.weight);
//在0~total范围内随机
int cursor = 0;
int random = Random.Range(0,totalWeight);
foreach(var item in randomConfigList)
{
//累加当前权重
cursor += item.weight;
//判断随机数
if(cursor > random)
{
return item;
}
}
return null;
}
}
测试代码,随机10000次,记录每个随机配置被随机到的次数
private void Start()
{
//定义随机参数权重
randomConfigList = new List<RandomConfig>() {
new RandomConfig(1,10),
new RandomConfig(2,20),
new RandomConfig(3,30),
new RandomConfig(4,40),
new RandomConfig(5,50),
};
//测试10000次,记录每次随机结果
Dictionary<RandomConfig,int> testResultDic = new Dictionary<RandomConfig,int>();
for(int i = 0; i < 10000; i++)
{
RandomConfig random = GetRandomValue();
if(testResultDic.ContainsKey(random))
testResultDic[random]++;
else
testResultDic[random] = 1;
}
//打印随机结果
foreach(var item in testResultDic)
{
Debug.Log(string.Format("随机返回值 : {0}; 权重 : {1}; 随机到次数 : {2}",item.Key.value,item.Key.weight,item.Value));
}
}
测试结果,大致与权重一致
扩展
每个随机配置有权重和可随机次数两个参数,权重影响随机概率,可随机次数表示能被随机到的次数上限。每次被随机到时,可随机次数减1,可随机次数为0时,从列表中剔除该随机数,以后不再参与随机。
public class NewBehaviourScript : MonoBehaviour
{
[System.Serializable]
public class RandomConfig
{
public RandomConfig(int v,int w,int c)
{
value = v;
weight = w;
count = c;
}
//返回值
public int value;
//随机权重
public int weight;
//可随机次数
public int count;
}
[SerializeField] private List<RandomConfig> randomConfigList = new List<RandomConfig>();
//---------
private RandomConfig GetRandomValue()
{
if(randomConfigList.Count <= 0)
return null;
List<RandomConfig> resultList = new List<RandomConfig>();
int totalWeight = randomConfigList.Aggregate(0,(all,next) => all += next.weight);
int cursor = 0;
int random = Random.Range(0,totalWeight);
foreach(var config in randomConfigList)
{
cursor += config.weight;
if(cursor > random)
{
config.count--;
if(config.count == 0)
randomConfigList.Remove(config);
return config;
}
}
return null;
}
}
测试代码,分别随机1000、5000、10000次,记录每个随机配置被随机到的次数
private void Start()
{
//定义随机参数权重
randomConfigList = new List<RandomConfig>() {
new RandomConfig(1,10,1000),
new RandomConfig(2,20,1000),
new RandomConfig(3,30,2000),
new RandomConfig(4,40,2000),
new RandomConfig(5,50,1000),
};
//测试10000次,记录每次随机结果
Dictionary<RandomConfig,int> testResultDic = new Dictionary<RandomConfig,int>();
for(int i = 0; i < 5000; i++)
{
RandomConfig random = GetRandomValue();
if(random == null)
continue;
if(testResultDic.ContainsKey(random))
testResultDic[random]++;
else
testResultDic[random] = 1;
}
//打印随机结果
foreach(var item in testResultDic)
{
Debug.Log(string.Format("随机返回值 : {0}; 权重 : {1}; 随机到次数 : {2}",item.Key.value,item.Key.weight,item.Value));
}
}
随机1000次
随机5000次
随机10000次
本文来自博客园,作者:萧然CS,转载请注明原文链接:https://www.cnblogs.com/z-c-s/p/15112843.html