![](/img/trans.png)
[英]How to implement division with round-towards-infinity in Python
[英]In Python, what is a good way to round towards zero in integer division?
1/2
給
0
正如它應該。 然而,
-1/2
給
-1
,但我希望它向 0 舍入(即我希望 -1/2 為 0),無論它是正數還是負數。 最好的方法是什么?
做浮點除法然后轉換為int。 不需要額外的模塊。
蟒蛇3:
>>> int(-1 / 2)
0
>>> int(-3 / 2)
-1
>>> int(1 / 2)
0
>>> int(3 / 2)
1
蟒蛇2:
>>> int(float(-1) / 2)
0
>>> int(float(-3) / 2)
-1
>>> int(float(1) / 2)
0
>>> int(float(3) / 2)
1
Python 的默認整數除法是返回下限(向負無窮大),無法改變它。 您可以閱讀BDFL 的原因。
要進行“四舍五入”除法,您可以使用:
>>> a=1
>>> b=2
>>> (a+(-a%b))//b
1
>>> a,b=-1,2
>>> (a+(-a%b))//b
0
要向零截斷並保持整數除法,如果 a 或 b 為負,則使用(a+(-a%b))//b
如果兩者均為正,則使用默認除法。
這將進行整數除法並始終向零舍入:
>>> a=1
>>> b=2
>>> a//b if a*b>0 else (a+(-a%b))//b
0
>>> a=-1
>>> b=2
>>> a//b if a*b>0 else (a+(-a%b))//b
0
>>> a,b=-3,2
>>> a//b if a*b>0 else (a+(-a%b))//b
-1
>>> a,b=3,2
>>> a//b if a*b>0 else (a+(-a%b))//b
1
有趣的是,C99 聲明向零舍入是默認值:
#include <stdio.h>
int main(int argc, const char * argv[])
{
int a=-3;
int b=2;
printf("a=%d, b=%d, a/b=%d\n",a,b,a/b);
a=3;
printf("a=%d, b=%d, a/b=%d\n",a,b,a/b);
return 0;
}
印刷:
a=-3, b=2, a/b=-1
a=3, b=2, a/b=1
對於它的價值,我自己最喜歡的解決方案是這個。 僅整數算術,單除法,以及其他所有線性時間:
def integer_divide_towards_zero(a, b):
return -(-a // b) if a < 0 else a // b
這假設b
是正數,但在我見過的大多數應用程序中都是如此。 如果您也需要處理負b
,那么該函數會變得稍微復雜一些:
def integer_divide_towards_zero(a, b):
return -(-a // b) if (a < 0) ^ (b < 0) else a // b
一些示例輸出:
>>> integer_divide_towards_zero(11, 3)
3
>>> integer_divide_towards_zero(-11, 3)
-3
>>> integer_divide_towards_zero(6, 3)
2
>>> integer_divide_towards_zero(-6, 3)
-2
>>> integer_divide_towards_zero(11, -3)
-3
>>> integer_divide_towards_zero(-11, -3)
3
嘗試這個。 僅適用於大於 -1 的數字
import math
x = .5
y = -.5
print math.floor(math.fabs(x))
>> 0
print math.floor(math.fabs(y))
>> 0
在我看來,執行此操作的正確代碼太晦澀,無法編寫為 1-liner。 所以我把它放在一個函數中,比如:
def int0div(a, b):
q = a // b
if q < 0 and b*q != a:
q += 1
return q
好的特性:它適用於任何大小的 int,除非必要,否則不對原始 ( a//b
) 結果進行任何調整,只進行一個除法( %
也在幕后進行除法),並且不創建任何大於輸入的整數。 這些在您的應用程序中可能重要也可能無關緊要; 如果您使用“大”整數,它們會變得更加重要(對於速度)。
提出一些替代想法:
將數字 [abs(x)/x] 的符號乘以 abs(x)/2
(abs(x)/x)*(abs(x)/2)
執行加法,但如果數字小於零,則加一使其更接近於 0。
x/2 + int(x<0)
為什么要重新發明輪子,當有一個非常好的 math.trunc() 函數時?
import math
print(math.trunc(-3.5))
>>-3
print(math.trunc(3.5))
>>3
聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.