如何在python中生成至少20位小数点后的种子随机浮点数?



我想在-1到1的范围内生成至少20位的种子随机浮点数。

import numpy as np
np.random.seed(2000)
np.random.uniform(low=-1, high=1, size=2)

这是我过去会做的,但我的能源部研究需要更精确。

我已经研究了python中的mpmath和decimal模块

import mpmath
mpmath.mp.dps = 22
xis = (mpmath.rand() - mpmath.mpf(1), mpmath.rand())

这不起作用,因为我找不到mpmath.mp.rand()种子的方法。

import numpy as np
from decimal import Decimal, getcontext
getcontext().prec = 20
xis = np.asarray([Decimal(f"{x}") x for x in np.random.uniform(low=-1, high=1, size=2)], dtype=np.float64)

这里,我的浮点数依赖于numpy,并且最大有16-7位小数。

如何创建具有20+小数点和可播种的随机浮点数?

一种朴素的方法:您可以在必要的范围内创建随机字符串字面量,并将它们提供给Decimal构造函数:

import random
from decimal import Decimal,getcontext
getcontext().prec = 20
def rand_decimal():
s = ''.join(random.choice('0123456789') for _ in range(20))
s = random.choice(['-','']) + '0.' + s
return Decimal(s)
for _ in range(10): print(rand_decimal())

典型输出:

-0.83346823024126032930
-0.84557526920081542182
-0.82525161638966954542
0.19433739638125145525
-0.21238635133910933910
0.53423291362045018461
0.01119989426218875072
-0.60199160675918881160
-0.53317266699396870741
-0.16609409040022211062

首先,您将需要~70位的精度来正确存储包含20位十进制数字的数字。IEEE754格式的long double(float96float128)具有80或106位的精度,这两个精度都足以满足任务。

遗憾的是,numpy.random.Generator.random只支持float32float64

基于目前mpmath.rand的python实现,随机性的来源只是标准库random模块,具体来说是random.getrandbits。通过调用通常的random.seed,您应该能够获得可重复的结果。不幸的是,状态是全局的:似乎没有一种机制可以使用单独的random.Random对象,例如,用于不同的线程。

请记住,您需要设置工作精度,这可以在上下文管理器中完成:

random.seed(my_seed)
with mp.workdps(22):
data = [mp.rand() for _ in range(my_size)]

如果你有一组脚本被作为模块导入,在你的主驱动程序中调用random.seed(my_seed)就足以初始化整个程序。

如果你在外部调用脚本,例如通过ossubprocess,你会想在每个脚本中放置相同的行。此时使用导入保护更安全,因此您可以不用考虑就以两种方式使用脚本:

if __name__ == '__main__':
random.seed(my_seed)