2013-10-22 126 views
1

我在与由numpy.arange生成的对象奇怪行为:奇怪行为,当铸造numpy.float64漂浮

for i in numpy.arange(xo, xn+h, h): 
    xs.append(float(i)) 

在这种情况下,xo=1xn=4h=0.1

现在,我预计xs[-1]是完全等于4.0 == float(4)。但是,我得到以下内容:

>>> foo = xs[-1] 
>>> foo == float(4) 
False 
>>> float(foo) == float(4) 
False 
>>> foo 
4.0 
>>> type(foo) 
<type 'float'> 
>>> int(sympy.ceiling(4.0)), int(sympy.ceiling(foo)) 
4 5 

这里发生了什么?

print type(i)放置在for循环打印<type 'numpy.float64'>。或许在float(i)投射期间发生了什么?使用numpy.asscalar不会改变任何东西。

使用math.ceil(foo)而不是sympy.ceiling(foo)发出相同的事情(这是我实际需要工作的部分)。

+0

numpy.float64 VS sympy.float?如果你使用sympy,你可能会遇到这样的问题,我猜? – usethedeathstar

+0

@usethedeathstar我使用内建的'float()'来进行投射。 Sympy仅用于上面控制台I/O的最后一行。而且,正如我所说的,使用'math.ceil'而不是'sympy.ceiling'返回相同的结果。 – Alex

+0

你应该避免使用浮点数的'np.arange'。而是使用'np.linspace'。 – seberg

回答

2
In [10]: for i in numpy.arange(xo, xn+h, h): 
     xs.append(float(i)) 
....:  

In [11]: xs 
Out[11]: 
[1.0, 
1.1, 
1.2000000000000002, 
1.3000000000000003, 
1.4000000000000004, 
1.5000000000000004, 
1.6000000000000005, 
1.7000000000000006, 
1.8000000000000007, 
1.9000000000000008, 
2.000000000000001, 
2.100000000000001, 
2.200000000000001, 
2.300000000000001, 
2.4000000000000012, 
2.5000000000000013, 
2.6000000000000014, 
2.7000000000000015, 
2.8000000000000016, 
2.9000000000000017, 
3.0000000000000018, 
3.100000000000002, 
3.200000000000002, 
3.300000000000002, 
3.400000000000002, 
3.500000000000002, 
3.6000000000000023, 
3.7000000000000024, 
3.8000000000000025, 
3.9000000000000026, 
4.000000000000003] 

这就是为什么你没有得到想要的结果,由于浮点精度,它不能给你的测试真。这也解释了为什么如果你做一个像天花板一样的圆形操作,你会得到五个而不是四个。

编辑: 检查,如果X和Y是相同的(一些误差之内),你能做到以下几点,但我认为这是(应该是)在Python的东西已经可以为您

做到这一点
def isnear(x,y, precision = 1e-5): 
    return abs(x-y)<precision 

EDIT2: 或ali_m说:

numpy.allclose(x, y, atol = 1e-5) 
+0

那么,在使用float(xs [-1])进行投射后,你会得到'4.0'作为输出,这让我感到奇怪。那么最好的方法是什么才能做到正确? '轮(我)'? – Alex

+0

@Alex我认为在python中有一些东西用来检查x是否接近y,如果你自己实现它,你可以尝试abs(xy) usethedeathstar

+1

@Alex:不是测试'f1 == f2',其中'f1'和'f2'都是浮点数,通常最好测试'abs(f1-f2) Simon

1

这并不奇怪 - 它只是浮点运算的工作方式,因为它不能完全代表大多数值。如果你重复计算浮点数(arange()这里是加0.1到1,然后再增加0.1到另一个29次),如果你处理的数字在浮点上不能精确表示,你将无法得到一个精确的在计算结束时回答。最好的文章阅读是What Every Computer Scientist Should Know About Floating-Point Arithmetic