极品predictable随机数发生器 [英] Need for predictable random generator

查看:161
本文介绍了极品predictable随机数发生器的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

我是一个web游戏开发人员,我有一个问题用随机数字。比方说,一个球员有20%的几率获得爆击与他的剑。这意味着,1出5命中应该是关键的。问题是,我得到了非常糟糕的现实生活的结果 - 有时球员得到3暴击5次点击,有时没有在15命中。战斗是相当短(3-10命中),因此重要的是要获得良好的随机分布。

I'm a web-game developer and I got a problem with random numbers. Let's say that a player has 20% chance to get a critical hit with his sword. That means, 1 out of 5 hits should be critical. The problem is I got very bad real life results -- sometimes players get 3 crits in 5 hits, sometimes none in 15 hits. Battles are rather short (3-10 hits) so it's important to get good random distribution.

目前我使用PHP mt_rand(),但我们只是将我们的code到C ++,所以我想解决我们的游戏的新引擎这个问题。

Currently I use PHP mt_rand(), but we are just moving our code to C++, so I want to solve this problem in our game's new engine.

我不知道解决的办法是有的均匀随机产生,或者记住previous随机状态,迫使适当的分配。

I don't know if the solution is some uniform random generator, or maybe to remember previous random states to force proper distribution.

推荐答案

我同意前面的答案,在一些游戏小批量真正的随机性是不可取的 - 这似乎太不公平了一些用例。

I agree with the earlier answers that real randomness in small runs of some games is undesirable -- it does seem too unfair for some use cases.

我用Ruby编写了一个简单的随机包一样实现和做了一些测试。实施这样做:

I wrote a simple Shuffle Bag like implementation in Ruby and did some testing. The implementation did this:

  • 如果它似乎仍然公平还是我们还没有达到最低轧辊的阈值,它返回一个基于正态概率公平的打击。
  • 如果从以往的辊所观察到的概率使得它看起来不公平,它返回一个公平ifying的打击。

这被认为是不公平的基于边界的概率。例如,对于20%的概率,可以设置10%的下限和40%作为上限。

It is deemed unfair based on boundary probabilities. For instance, for a probability of 20%, you could set 10% as a lower bound and 40% as an upper bound.

使用的范围,我发现有10个安打,运行时间 14.2%,真正的伪随机执行产生的是出这些边界的结果。约11%的时间,0会心一击拿下了10次尝试。的时间为3.3%,5个或更多临界命中物降落出10。自然地,使用这种算法(为5的最小辊计数),其中的还可以的奔跑小得多的量(0.03%)为出界。即使下面的实现是不合适的(更聪明的事情可以做,肯定),值得一提的是,noticably通常用户会觉得这是一个真正的伪解决方案不公平的。

Using those bounds, I found that with runs of 10 hits, 14.2% of the time the true pseudorandom implementation produced results that were out of those bounds. About 11% of the time, 0 critical hits were scored in 10 tries. 3.3% of the time, 5 or more critical hits were landed out of 10. Naturally, using this algorithm (with a minimum roll count of 5), a much smaller amount (0.03%) of the "Fairish" runs were out of bounds. Even if the below implementation is unsuitable (more clever things can be done, certainly), it is worth noting that noticably often your users will feel that it's unfair with a real pseudorandom solution.

下面是我的 FairishBag 用Ruby写的肉。整个实施和快速蒙特卡罗模拟可以在这里(GIST)

Here is the meat of my FairishBag written in Ruby. The whole implementation and quick Monte Carlo simulation is available here (gist).

def fire!
  hit = if @rolls >= @min_rolls && observed_probability > @unfair_high
    false
  elsif @rolls >= @min_rolls && observed_probability < @unfair_low
    true
  else
    rand <= @probability
  end
  @hits += 1 if hit
  @rolls += 1
  return hit
end

def observed_probability
  @hits.to_f / @rolls
end

更新:使用这种方法并增加患上致命一击,约22%使用上述范围的总概率。您可以通过设置它的真实的概率低一点抵消。的17.5%与还可以的修改的概率产生了约20%的所观察到的长期的概率,并保持短期运行感觉公平

Update: Using this method does increase the overall probability of getting a critical hit, to about 22% using the bounds above. You can offset this by setting its "real" probability a little bit lower. A probability of 17.5% with the fairish modification yields an observed long term probability of about 20%, and keeps the short term runs feeling fair.

这篇关于极品predictable随机数发生器的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆