我有一个介于0和1之间的变量,它应该指示 mighthood 第二个变量,0到1之间的随机数,大于0.5。换句话说,如果我要生成第二个变量1000次,则平均值应大约等于第一个变量的值。我该如何制作这段代码?
哦,第二个变量应该始终能够在任何条件下产生0或1,或多或少取决于第一个变量的值。这是一个link to a graph,它模拟了我希望程序的行为方式。每个等式代表第一个变量的单独值。
答案 0 :(得分:3)
您有一个变量p
,并且您正在寻找一个映射函数f(x)
,它将x in [0, 1]
之间的随机卷映射到相同的间隔[0, 1]
,以便达到预期值,即所有卷的平均值为p
。
您选择了函数原型
f(x) = pow(x, c)
必须适当选择c
。如果x
均匀分布在[0, 1]
中,则平均值为:
int(f(x) dx, [0, 1]) == p
使用积分:
int(pow(x, c) dx) == pow(x, c + 1) / (c + 1) + K
一个人得到:
c = 1/p - 1
另一种方法是使p
为分布的中值,使得一半的卷低于p
,另一半高于p
。这产生了不同的分布。 (我知道你没有要求。)现在,我们必须满足条件:
f(0.5) == pow(0.5, c) == p
产生:
c = log(p) / log(0.5)
使用当前的函数原型,您无法满足这两个要求。您的功能也是不对称的(f(x, p) != f(1-x, 1-p)
)。
下面的Python函数:
def medianrand(p):
"""Random number between 0 and 1 whose median is p"""
c = math.log(p) / math.log(0.5)
return math.pow(random.random(), c)
def averagerand(p):
"""Random number between 0 and 1 whose expected value is p"""
c = 1/p - 1
return math.pow(random.random(), c)
答案 1 :(得分:0)
你可以通过使用假人来做到这一点。首先将第一个变量设置为0到1之间的值。然后在0到1之间的虚拟中创建一个随机数。如果此虚拟对象大于第一个变量,则生成0到0.5之间的随机数,否则生成数字介于0.5和1之间。
在伪代码中:
real a = 0.7
real total = 0.0
for i between 0 and 1000 begin
real dummy = rand(0,1)
real b
if dummy > a then
b = rand(0,0.5)
else
b = rand(0.5,1)
end if
total = total + b
end for
real avg = total / 1000
请注意,此算法将生成介于0.25和0.75之间的平均值。对于a = 1,它只会生成介于0.5和1之间的随机值,这应该平均为0.75。对于a = 0,它将仅生成0到0.5之间的随机数,其平均值应为0.25。
答案 2 :(得分:0)
我已经对这个问题做了一种伪解决方案,我认为这是可以接受的。
这是我制作的算法;
a = 0.2 # variable one
b = 0 # variable two
b = random.random()
b = b^(1/(2^(4*a-1)))
它实际上并没有产生我想要的平均结果,但它足够接近我的目的。
编辑:Here's a graph我创建的是由我使用此算法生成的python脚本生成的大量数据点;
import random
mod = 6
div = 100
for z in xrange(div):
s = 0
for i in xrange (100000):
a = (z+1)/float(div) # variable one
b = random.random() # variable two
c = b**(1/(2**((mod*a*2)-mod)))
s += c
print str((z+1)/float(div)) + "\t" + str(round(s/100000.0, 3))
表中的每个点都是算法中随机生成的100000个点的结果;他们的x位置是给定的值,他们的y位置是他们的平均值。理想情况下,它们适合y = x
的直线,但正如您所看到的那样,它们更接近于arctan方程。我试图搞乱这个算法,以便平均值适合这条线,但我还没有多少运气。