在Python 2.x中,内置函数round具有以下行为:
如果两个倍数相等,则舍入远离0(因此,例如,round(0.5)为1.0,round(-0.5)为-1.0)
在Python 3.x中,这已经变为更常见的:
如果两个倍数相等,则向均匀选择进行舍入(例如,圆形(0.5)和圆形(-0.5)都是0,圆形(1.5)是2).
有没有一种简单的方法可以在Python 2.x中获得这种行为?不幸的是,该future_builtins模块不包括此内容.也许还有另一个类似的模块我还没找到?或者,将Python 3.x函数引入Python 2.x的另一种方法是什么?
显然,我可以编写一个产生所需行为的新函数,但是如果存在使用实际Python 3.x函数的解决方案,我会更加好奇,以避免添加不必要的复杂性和代码来维护.
Python 3 转入 Python 2
该函数可以如下所示:
def py3round(f):
if abs(round(f)-f) == 0.5:
return 2.0*round(f/2.0);
return round(f)
# Python 3 apply round to ... -.1 -.75 -.5 -.25 0 .25 .5 .75 ...
>>> ' '.join(map(str, map(int, [round(i * 0.25) for i in range(-20, 20)])))
'-5 -5 -4 -4 -4 -4 -4 -3 -3 -3 -2 -2 -2 -2 -2 -1 -1 -1 0 0 0 0 0 1 1 1 2 2 2 2 2 3 3 3 4 4 4 4 4 5'
# Python 2 apply round to ... -.1 -.75 -.5 -.25 0 .25 .5 .75 ...
>>> ' '.join(map(str, map(int, [py3round(i * 0.25) for i in range(-20, 20)])))
'-5 -5 -4 -4 -4 -4 -4 -3 -3 -3 -2 -2 -2 -2 -2 -1 -1 -1 0 0 0 0 0 1 1 1 2 2 2 2 2 3 3 3 4 4 4 4 4 5'
Run Code Online (Sandbox Code Playgroud)
让我澄清一下 round 的作用bltinmodule.c
if hasattr(args[0], '__round__'):
return args[0].__round__(*args[1:])
else:
raise TypeError("type %.100s doesn't define __round__ method")
Run Code Online (Sandbox Code Playgroud)
所以 round 实际上几乎什么也没做。这取决于传递给它的对象。这导致floatobject.c功能static PyObject *double_round(double x, int ndigits)
z = round(y);
if (fabs(y-z) == 0.5)
/* halfway between two integers; use round-half-even */
z = 2.0*round(y/2.0);
Run Code Online (Sandbox Code Playgroud)
我在上面的函数中使用了这些行的知识。
Python 2 转入 Python 3
我认为你需要编写一个新函数。
def python2round(f):
if round(f + 1) - round(f) != 1:
return f + abs(f) / f * 0.5
return round(f)
Run Code Online (Sandbox Code Playgroud)
i + 0.5if 语句处理和被四舍五入到不同方向的情况i + 1.5= 为偶数和二等分。在这种情况下,舍入是从零开始的。
# in Python 2 apply round to ... -.1 -.75 -.5 -.25 0 .25 .5 .75 ...
>>> ' '.join(map(str, map(int, [round(i * 0.25) for i in range(-20, 20)])))
'-5 -5 -5 -4 -4 -4 -4 -3 -3 -3 -3 -2 -2 -2 -2 -1 -1 -1 -1 0 0 0 1 1 1 1 2 2 2 2 3 3 3 3 4 4 4 4 5 5'
# in Python 3 apply round to ... -.1 -.75 -.5 -.25 0 .25 .5 .75 ...
>>> ' '.join(map(str, map(int, [python2round(i * 0.25) for i in range(-20, 20)])))
'-5 -5 -5 -4 -4 -4 -4 -3 -3 -3 -3 -2 -2 -2 -2 -1 -1 -1 -1 0 0 0 1 1 1 1 2 2 2 2 3 3 3 3 4 4 4 4 5 5'
Run Code Online (Sandbox Code Playgroud)
您是否需要使用第二个参数进行舍入的解决方案ndigits?
除非您介意麻木的依赖关系,numpy.around否则可以执行以下操作:
>>> from numpy import around
>>> around(0.5)
0
>>> around(-0.5)
-0
>>> around(1.5)
2.0
Run Code Online (Sandbox Code Playgroud)