对数字Python 3.2进行舍入时的“量化”

时间:2012-10-03 05:11:41

标签: python math python-3.x rounding

我正试图在数学运算后找到一种方法将数字捕捉或量化为特定值,并且不知道解决问题的最佳方法。

一个具体的例子:

我有一个数字列表,我想成为我的主号码 - 5,10,30,60,120,180

我有一个当前输入的数字列表 - 10,20,60,120

现在我想将所有输入的数字乘以2,然后将它们捕捉(或量化/舍入到)最接近的主数字。

所以一个像10这样的数字,一旦乘以2,我想让它突然变为30.我不认为它是顶部或底部的大问题,因为我认为我可以使用math.ceil和math.floor包含两端。同样地,我希望20也可以舍入为30(20 * 2 = 40,向下舍入为30,接近60)。

我在圆形到10s,100s等方面看到了类似的问题,但无法真正弄清楚如何在那里应用答案,因为我还是比较新的! :)

2 个答案:

答案 0 :(得分:2)

对于x的元素input,找到x*2masterx*2的每个元素的绝对差异,然后找到该新列表的最小值将是四舍五入的数字。

代表。对于输入列表中的20,绝对差异列表将是:

[abs(5-40),abs(10-40),abs(30-40),abs(60-40),abs(120-40),abs(180-40)]

导致[35,30,10,20,80,140]3rd元素的最小差异,即30列表的master

In [14]: inp=[10, 20, 60, 120,17,27,50]

In [15]: master=[5, 10, 30, 60, 120, 180]

In [16]: [min(master,key=lambda y:abs(y-x*2)) for x in inp]
Out[16]: [10, 30, 120, 180, 30, 60, 120]

答案 1 :(得分:2)

使用bisect模块快速查明所需数量:

import bisect

def quantize(num, quant):
    mids = [(quant[i] + quant[i + 1]) / 2.0
            for i in xrange(len(quant) - 1)]
    ind = bisect.bisect_right(mids, num)
    return quant[ind]

quantnum = [5, 10, 30, 60, 120, 180]

inputnum = [10, 20, 60, 120]

for n in inputnum:
    print quantize(2 * n, quantnum)

# Output:
#30
#30
#120
#180

中点四舍五入到更大的数量;将bisect_right更改为bisect_left以转换为较小的一个。

为简单起见,此实现在每次调用时都会重新创建mids列表。一个有效的实现将重用中点,并将以O(log n)最坏情况的复杂性运行。