算法名称 Alias Method
public class AliasMethod {
/* The probability and alias tables. */
private int[] _alias;
private double[] _probability;
public AliasMethod(List<Double> probabilities) {
/* Allocate space for the probability and alias tables. */
_probability = new double[probabilities.Count];
_alias = new int[probabilities.Count];
/* Compute the average probability and cache it for later use. */
double average = 1.0 / probabilities.Count;
/* Create two stacks to act as worklists as we populate the tables. */
var small = new Stack<int>();
var large = new Stack<int>();
/* Populate the stacks with the input probabilities. */
for (int i = ; i < probabilities.Count; ++i) {
/* If the probability is below the average probability, then we add
* it to the small list; otherwise we add it to the large list.
*/
if (probabilities[i] >= average)
large.Push(i);
else
small.Push(i);
}
/* As a note: in the mathematical specification of the algorithm, we
* will always exhaust the small list before the big list. However,
* due to floating point inaccuracies, this is not necessarily true.
* Consequently, this inner loop (which tries to pair small and large
* elements) will have to check that both lists aren't empty.
*/
while (small.Count > && large.Count > ) {
/* Get the index of the small and the large probabilities. */
int less = small.Pop();
int more = large.Pop();
/* These probabilities have not yet been scaled up to be such that
* 1/n is given weight 1.0. We do this here instead.
*/
_probability[less] = probabilities[less] * probabilities.Count;
_alias[less] = more;
/* Decrease the probability of the larger one by the appropriate
* amount.
*/
probabilities[more] = (probabilities[more] + probabilities[less] - average);
/* If the new probability is less than the average, add it into the
* small list; otherwise add it to the large list.
*/
if (probabilities[more] >= average)
large.Push(more);
else
small.Push(more);
}
/* At this point, everything is in one list, which means that the
* remaining probabilities should all be 1/n. Based on this, set them
* appropriately. Due to numerical issues, we can't be sure which
* stack will hold the entries, so we empty both.
*/
while (small.Count > )
_probability[small.Pop()] = 1.0;
while (large.Count > )
_probability[large.Pop()] = 1.0;
}
/**
* Samples a value from the underlying distribution.
*
* @return A random value sampled from the underlying distribution.
*/
public int next() {
long tick = DateTime.Now.Ticks;
var seed = ((int)(tick & 0xffffffffL) | (int)(tick >> ));
unchecked {
seed = (seed + Guid.NewGuid().GetHashCode() + new Random().Next(, ));
}
var random = new Random(seed);
int column = random.Next(_probability.Length);
/* Generate a biased coin toss to determine which option to pick. */
bool coinToss = random.NextDouble() < _probability[column];
return coinToss ? column : _alias[column];
}
}
Dictionary<String, Double> map = new Dictionary<String, Double>();
map.Add("1金币", 0.2);
map.Add("2金币", 0.15);
map.Add("3金币", 0.1);
map.Add("4金币", 0.05);
map.Add("未中奖", 0.5); List<Double> list = new List<Double>(map.Values);
List<String> gifts = new List<String>(map.Keys); AliasMethod method = new AliasMethod(list); Dictionary<String, int> resultMap = new Dictionary<String, int>(); for (int i = ; i < ; i++) {
int index = method.next();
string key = gifts[index];
Console.WriteLine(index+":"+key);
}
源文:https://www.cnblogs.com/ahjesus/p/6038015.html
算法名称 Alias Method的更多相关文章
- 茅坑杀手与Alias Method离散采样
说起Alias,你可能第一个联想到的是Linux中的Alias命令,就像中世纪那些躲在茅坑下面(是真的,起码日本有粪坑忍者,没有马桶的年代就是社会的噩梦)进行刺杀的杀手一样,让人防不胜防,对于那些被这 ...
- Alias Method解决随机类型概率问题
举个例子,游戏中玩家推倒了一个boss,会按如下概率掉落物品:10%掉武器 20%掉饰品 30%掉戒指 40%掉披风.现在要给出下一个掉落的物品类型,或者说一个掉落的随机序列,要求符合上述概率. 一般 ...
- java加密类型和算法名称
项目里有各种加密方法,但从来没有仔细研究过.一般只是copy.这几天遇到一些问题,看了一下加密代码,觉得有些疑惑. 我们知道jdk已经为我们包装好了很多的算法.但究竟包装了哪些算法,怎么去掉这些算法我 ...
- Alias Method for Sampling 采样方法
[Alias Method for Sampling]原理 对于处理离散分布的随机变量的取样问题,Alias Method for Sampling 是一种很高效的方式. 在初始好之后,每次取样的复杂 ...
- 封装算法: 模板方法(Template Method)模式
template method(模板方法)模式是一种行为型设计模式.它在一个方法中定义了算法的骨架(这种方法被称为template method.模板方法),并将算法的详细步骤放到子类中去实现.tem ...
- paper 142:SDM算法--Supervised Descent Method
对于face recognition的研究,我是认真的(认真expression,哈哈哈~~~~~~)许久没有写blog了,欢迎一起讨论. SDM(Supvised Descent Method)方法 ...
- 三维网格补洞算法(Poisson Method)
下面介绍一种基于Poisson方程的三角网格补洞方法.该算法首先需要根据孔洞边界生成一个初始化补洞网格,然后通过法向估算和Poisson方程来修正补洞网格中三角面片的几何形状,使其能够适应并与周围的原 ...
- 三维网格补洞算法(Poisson Method)(转载)
转载:https://www.cnblogs.com/shushen/p/5864042.html 下面介绍一种基于Poisson方程的三角网格补洞方法.该算法首先需要根据孔洞边界生成一个初始化补洞网 ...
- c#中奖算法的实现
算法名称 Alias Method public class AliasMethod { /* The probability and alias tables. */ private int[] _ ...
随机推荐
- fiddler证书问题
1.清除C:\Users\Administrator\AppData\Roaming\Microsoft\Crypto\RSA 目录下所有文件(首次安装fiddler请忽略) 2.清除电脑上的根证书, ...
- 解决加载WEB页面时,由于JS文件引用过多影响页面打开速度的问题
1.一般做法 一般我们会把所有的<script>元素都应该放在页面的<head>标签里,但由于是顺序加载,因此只有当所有JavaScript代码都被依次下载.解析和执行完之后, ...
- CENTOS6.5源码安装LNMP
CENTOS6.5源码安装LNMP 一.安装前准备 ########################################################################## ...
- 六、Linux_SSH服务器状态
一.保持Xshell连接Linux服务器状态 1.登录服务器后 cd /etc/ssh/ vim sshd_config 找到 ClientAliveInterval 0和ClientAliveCou ...
- 深层次揭示runBlocking与coroutineScope之间的异同点
在之前https://www.cnblogs.com/webor2006/p/11731763.html咱们写过这样的一个例子,先来回顾一下: 也就是来演示runBlocking与coroutineS ...
- Kotlin字节码生成机制详尽分析
通过注解修改Kotlin的class文件名: 对于Kotlin文件在编译之后生成的class文件名默认是有一定规则的,比如: 而其实这个生成字节码的文件名称是可以被改的,之前https://www.c ...
- Spring Cloud Zuul网关(快速搭建)
zuul 是netflix开源的一个API Gateway 服务器, 本质上是一个web servlet应用. 在云平台上提供动态路由,监控,弹性,安全等边缘服务的框架.相当于是设备和 Netflix ...
- cifar-10数据集的可视化
import numpy as np from PIL import Image import pickle import os CHANNEL = 3 WIDTH = 32 HEIGHT = 32 ...
- 利用GitHub+Node.js+Hexo搭建个人博客
本篇是自己在搭建Hexo博客平台时的一个过程记录.(2019.9.13实测有效) GitHub 账号注册 因为此文所搭建的个人博客是基于GitHub平台服务的,所以首先是注册GitHub,当然已有账号 ...
- 【批处理】for命令
for 命令 学习:https://www.cnblogs.com/Braveliu/p/5081087.html FOR这条命令基本上都被用来处理文本,但还有其他一些好用的功能! 看看他的基本格式( ...