- iOS/Objective-C 元类和类别
- objective-c - -1001 错误,当 NSURLSession 通过 httpproxy 和/etc/hosts
- java - 使用网络类获取 url 地址
- ios - 推送通知中不播放声音
我可以使用两种方法中的一种来创建具有两个重要特征的伪随机数序列 - (1) 它可以在不同的机器上重现,并且 (2) 该序列从不重复范围内的数字,直到所有数字都被发出.
我的问题是 - 这些方法中的任何一种在可移植性(操作系统、Python 版本等)方面是否存在潜在问题?例如,有谁知道当 XXX 为真时我是否会在一个系统上获得一组结果而在另一个系统上获得不同的结果?
我并不是真的征求关于使用哪种方法本身的建议,只是当 Z 为真时我应该注意 Y 系统上的 X。
我试过几个 Linux 版本,都是 64 位的,它们看起来一致,但我无法轻松访问 Windows 或 32 位版本。
请注意,它们不会产生彼此相同的范围,但这对我来说没问题。这些数字只需要在人眼看来是随机的。
方法 1
使用 native Python 库函数从一个范围内生成一个随机样本。如果我使用大范围(10m 或更大),它会很慢,但对于相对较小的范围来说还可以,并且对于没有数学学位的人来说更容易理解:
import random
random.seed(5)
x = random.sample(range(10000,99999),89999)
for i in range(10):
print(x[i])
方法 2
使用的算法不是来自 Python 库:
( https://en.wikipedia.org/wiki/Linear_congruential_generator )
即使对于大范围,它也非常快,但更难理解,因此发现潜在问题:
def lcg(modulus, a, c, seed):
while True:
seed = (a * seed + c) % modulus
yield seed
m = 10000019
c = int(m/2)
a = 5653
s = a
g = lcg(m,a,c,s)
for _ in range(10):
print(next(g))
请注意,我对其他选择持开放态度;最初的问题是在这里提出的:https://math.stackexchange.com/questions/3289084/generate-a-pseudo-random-predictable-non-repeating-integer-sequence-purely-math
最佳答案
大多数便携版本,IMO,将是周期等于机器自然字大小的 LCG。它为模块使用寄存器溢出,使其更快。你必须使用 NumPy 数据类型来做到这一点,这里是简单的代码,常量 a、c 取自表 4 here
import numpy as np
def LCG(seed: np.uint64, a: np.uint64, c: np.uint64) -> np.uint64:
with np.errstate(over='ignore'):
while True:
seed = (a * seed + c)
yield seed
a = np.uint64(2862933555777941757)
c = np.uint64(1)
rng64 = LCG(np.uint64(17), a, c)
print(next(rng64))
print(next(rng64))
print(next(rng64))
Linux x64 和 Windows x64 以及 OS X VM 的工作方式完全相同。
关于可重复性,唯一的好处是存储前几个数字并在应用程序初始化阶段将它们与 LCG 输出进行比较 - 如果它们没问题,您可以继续进行。
我喜欢 LCG 的另一个特点是它能够在 log2(N) 时间内向前跳跃,其中 N 是跳跃次数。我可以为您提供代码来做到这一点。使用 jump ahead 可以确保并行独立随机流的非重叠序列
更新
这里是我的 C 代码到 Python/NumPy 的翻译,似乎有效。它可以在对数时间向前和向后跳跃。
import numpy as np
class LCG(object):
UZERO: np.uint64 = np.uint64(0)
UONE : np.uint64 = np.uint64(1)
def __init__(self, seed: np.uint64, a: np.uint64, c: np.uint64) -> None:
self._seed: np.uint64 = np.uint64(seed)
self._a : np.uint64 = np.uint64(a)
self._c : np.uint64 = np.uint64(c)
def next(self) -> np.uint64:
self._seed = self._a * self._seed + self._c
return self._seed
def seed(self) -> np.uint64:
return self._seed
def set_seed(self, seed: np.uint64) -> np.uint64:
self._seed = seed
def skip(self, ns: np.int64) -> None:
"""
Signed argument - skip forward as well as backward
The algorithm here to determine the parameters used to skip ahead is
described in the paper F. Brown, "Random Number Generation with Arbitrary Stride,"
Trans. Am. Nucl. Soc. (Nov. 1994). This algorithm is able to skip ahead in
O(log2(N)) operations instead of O(N). It computes parameters
A and C which can then be used to find x_N = A*x_0 + C mod 2^M.
"""
nskip: np.uint64 = np.uint64(ns)
a: np.uint64 = self._a
c: np.uint64 = self._c
a_next: np.uint64 = LCG.UONE
c_next: np.uint64 = LCG.UZERO
while nskip > LCG.UZERO:
if (nskip & LCG.UONE) != LCG.UZERO:
a_next = a_next * a
c_next = c_next * a + c
c = (a + LCG.UONE) * c
a = a * a
nskip = nskip >> LCG.UONE
self._seed = a_next * self._seed + c_next
np.seterr(over='ignore')
a = np.uint64(2862933555777941757)
c = np.uint64(1)
seed = np.uint64(1)
rng64 = LCG(seed, a, c) # initialization
print(rng64.next())
print(rng64.next())
print(rng64.next())
rng64.skip(-3) # back by 3
print(rng64.next())
print(rng64.next())
print(rng64.next())
rng64.skip(-3) # back by 3
rng64.skip(2) # forward by 2
print(rng64.next())
无论如何,LCG RNG 的总结:
关于python - RNG 技术的便携性和可重复性,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/56983355/
原谅那个疯狂的标题... 我试图理解面向对象编程中继承与接口(interface)的概念。所以我试图将它与我已经知道的东西联系起来,这就是 CSS。 在 CSS 中,您可以选择在允许元素“继承”样式的
我有一个 C 函数,它返回一个表示二进制数据的 unsigned char*。我在文档中注意到 SWIG 有一个很好的类型映射来处理二进制数据作为 C 函数的输入,但是当 C 函数返回二进制数据及其无
过去遇到过几次类似的问题,想知道用什么语言(方法)来解决类似的问题(我是J2EE/java开发人员): 问题:在一组可能的单词中,根据给定的规则(假设单词可以是 A 和 X 的组合,并且始终以 X 开
这个问题不太可能帮助任何 future 的访客;它只与一个小地理区域、一个特定时刻或一个非常狭窄的情况相关,而这些情况通常不适用于互联网的全局受众。如需帮助使这个问题更广泛地适用,visit the
如果我们已经开发了自己的ORM框架并且该框架在过去的几年中运行良好,那么为什么我们要为即将到来的软件项目学习和使用全新的.net技术,例如LINQ或Entity Framework或NHibernat
即使听起来很奇怪,我相信每个人在处理具有大量自定义组件的大型应用程序时都遇到过此类问题。某个地方生成了 AV,但应用程序仍在继续执行,稍后会出现错误。我不是在谈论多线程应用程序。只是关于通用的单线程应
我正在设计一个新项目,我正在尝试找出将数据/事件从服务器应用程序推送到客户端应用程序(即 WPF 应用程序)的方法。 我知道的两个是: 发布/订阅(即 NServiceBus) Full Duplex
关闭。这个问题不满足Stack Overflow guidelines .它目前不接受答案。 想改善这个问题吗?更新问题,使其成为 on-topic对于堆栈溢出。 5年前关闭。 Improve thi
这个问题在这里已经有了答案: C# .NET: How to check if we're running on battery? (6 个答案) 关闭 9 年前。 我发现许多 API 可以帮助确定
没有 JQUERY!我有一个下拉列表,用户可以在其中选择日期、月份和年份。我创建以下代码并使用 setFullYear 将这些值传递到变量中。有时我还会向这个变量添加天数,这就是变量 ev_num 的
我有一个控件,我想在表单和打印时以不同的方式绘制它。这是我做的方式: private void printDocument1_PrintPage(object sender, System.Drawi
我正在尝试确定从扫描文档中提取手写数据的最佳方法。 手写数据位于特定的方框区域。我生成了文档的数字版本,因此我知道方框区域的坐标,并且如果需要还可以生成文档的其他变体(即被屏蔽以使字段更容易提取的版本
背景 对于基于音乐的问题,我深表歉意,但细节并没有那么重要。我正在按顺序浏览一个 midi 文件,我正在寻找一种有效的方法来查找数据中的模式以找到称为连音符的东西。见下图: 连音符上方有数字(3 或
经验丰富的 Java 新手,寻求您的智慧: 如果无法确保在对象超出范围时执行某些特定的 block 代码,那么还有哪些其他方法可以提供相同的功能?(看起来 finalize 显然不是那个意思) 一个典
我正在玩一个小的油漆应用程序。我想创建不同的画笔提示(不仅仅是简单的线条)。基本思想是沿着鼠标移动重复(冲压)画笔 Nib 。因为鼠标移动不会为鼠标移动的每个像素分派(dispatch)所需的事件。我
我正在制作时间表应用程序。重要的类是: Period id: int clazz: Clazz SubjectTeacher subject: String teac
关闭。这个问题需要更多 focused .它目前不接受答案。 想要改进这个问题吗? 更新问题,使其只关注一个问题 editing this post . 关闭 4 年前。 Improve this q
我有一个奇怪的任务要解决。我们有一个小型视频窗口(如 300x200 像素,256 色调色板)和 44kHz 2ch 声音在服务器上播放。我们需要将此流视频发送给一些客户端(1,2.. 最多 10 个
我很确定我在这里遗漏了一些东西,因为我对 Shapeless 还很陌生并且我正在学习,但是 Aux 技术实际上什么时候开始需要 ?我看到它是用来暴露一个 type通过将其提升为另一个“同伴”的签名来声
微软有什么理由仍然坚持使用 COM 技术(Office 组件仍然是 COM)……当所有用 COM 完成的事情都可以用 .Net 以更好、更有效的方式完成时 最佳答案 因为它需要一个 长完全重写Offi
我是一名优秀的程序员,十分优秀!