这可能是一个奇怪的问题,但在这里:
我有一个数值模拟.这不是一个特别长的计划,但有点冗长来解释它正在做什么.我运行模拟一千次并计算平均结果和方差,方差非常小,大约为10 ^( - 30).
但是,我注意到当我在python 3.3中运行程序时,事情变得奇怪了.参见Python 2.7和Python 3.2我每次都会得到相同的答案.相同的平均值,相同的微小差异.
但是当我在Python 3.3中运行它时,我每次都得到一个不同的答案.也就是说,不同的平均值和不同(但仍然很小)的差异.这是非常奇怪的,因为概率定律表明,如果方差实际上很小,就不会发生这种情况.所以我想知道,自3.2以来改变的3.3解释器到底发生了什么,这导致我的模拟变得疯狂?
以下是我想到的一些事情:
在我的Python版本中,我可能有一个奇怪的32位/ 64位差异,但我没有检查过它们都运行64位.
我可能在float/int转换中有一些错误,但是这将在Python 3.2中处理,因为它们在适当的时候使得除法返回浮点数,因此3.2和3.3结果应该是相同的.
我的模拟被表示为生成器,因此可能在3.3中使用生成器进行了更改,但我无法分辨它是什么.
我不知道数值浮点表示有一些变化.
其中一个函数中存在一些潜在的变化,其结果是"未确定的",这会影响我的算法的初始条件.例如,在我的代码中的某处,我使用"list(table.keys())命令我的数据列最初是一个字典",并且列表决定如何从3.2到3.3排序字典键可能有所改变.但如果是这种情况,那么代码应该每次都做同样的事情,但事实并非如此(故意使列表的排序随机化似乎很奇怪!).
有没有人指出可能导致我的问题从3.2变为3.3的变化?
你的最后一个要点很可能是原因.在python3.3中,默认情况下启用了哈希随机化以解决安全问题.基本上,这个想法是你现在永远不知道你的字符串将如何哈希(这决定了它们在字典中的顺序).
这是一个演示:
d = {"a": 1, "b": 2, "c": 3} print(d)
在我的机器上,使用python3.4,这会得到3个不同排序的结果:
$ python3.4 test.py {'a': 1, 'c': 3, 'b': 2} $ python3.4 test.py {'c': 3, 'b': 2, 'a': 1} $ python3.4 test.py {'b': 2, 'c': 3, 'a': 1}
在散列随机化之前,如果您知道字符串将如何散列,则具有足够应用程序知识的恶意攻击者可以将其数据提供给导致字典查找在O(n)时间运行而不是通常的O(1)进行字典查找.这可能会导致某些应用程序性能严重下降.
您可以禁用此处记录的哈希随机化.在某些时候,他们还-R
为python 引入了一个标志,该标志在"选择加入"的基础上启用了散列随机化.此选项至少可用于python3.2,因此您可以使用它来测试我们的假设.