分數

分數 在 Python

{other: "%{count} 個練習"}

關於 分數

fractions 模組讓我們可以建立並操作rational numbers:也就是分子為整數、分母也為整數的分數。

例如,我們可以把 2/3 存成精確的分數,而不是近似的float值0.6666...。

建立分數

和 int、float、complex 這些數字不同,分數沒有字面值的寫法。 不過,分數建構子的彈性相當大。

最明顯的是,它可以接受兩個整數。 公因數會自動約掉,把分數化成「最簡形式」(能精確表示這個分數的最小整數):

>>> from fractions import Fraction

>>> f1 = Fraction(2, 3) # 2/3
>>> f1
Fraction(2, 3)

>>> f2 = Fraction(6, 9)
>>> f2
Fraction(2, 3)  # automatically simplified

>>> f1 == f2
True

分數建構子也可以解析字串表示法:

>>> f3 = Fraction('2/3')
>>> f3
Fraction(2, 3)

它也可以搭配 float 參數運作,但這可能會碰上問題,因為小數值在內部是以二進位近似表示的。 關於這個表示法問題的更多說明,請參閱 0.30000000000000004 網站,以及 Python 文件中的 浮點數運算:問題與限制 。

若想在分數中使用浮點數時獲得更可靠的結果,可以使用<fraction>.limit_denominator()方法。

.limit_denominator()可以接受一個整數參數,如果你有特定需求的話;不過即使是預設值(max_denominator=1000000)也能運作良好,給出可接受又簡單的近似值。

>>> Fraction(1.2)
Fraction(5404319552844595, 4503599627370496)

>>> Fraction(1.2).limit_denominator()
Fraction(6, 5)

分數的算術運算

和其他數值型別一樣,常見的arithmetic operators+ - * / **也能用在分數上。

整數和其他 Fraction 可以一起參與運算,結果仍是 Fraction。 運算式裡只要包含 float,輸出就會是 float,因此可能造成精度損失。

>>> Fraction(2, 3) + Fraction(1, 4) # addition
Fraction(11, 12)

>>> Fraction(2, 3) * Fraction(6, 5) # multiply fractions
Fraction(4, 5)

>>> Fraction(2, 3) * 6 / 5 # fraction with integers
Fraction(4, 5)

>>> Fraction(2, 3) * 1.2  # fraction with float -> float
0.7999999999999999

>>> Fraction(2, 3) ** 2  # exponentiation with integer
Fraction(4, 9)

分數的轉換

分數很適合在計算過程中保留精度,但可能不是你想要的最終輸出。

可以個別取得分子和分母,或是以元組的形式取得(tuples會在之後的概念中討論):

>>> Fraction(2, 3).numerator
2
>>> Fraction(2, 3).denominator
3
>>> Fraction(2, 3).as_integer_ratio()
(2, 3)

各種標準的 Python 數值函式,也會給出和處理int、float型別時相同的結果:

>>> round(Fraction(11, 3))
4

>>> from math import floor, ceil
>>> floor(Fraction(11, 3))
3
>>> ceil(Fraction(11, 3))
4

>>> float(Fraction(11, 3))
3.6666666666666665
透過 GitHub 編輯 連結會在新視窗或分頁中開啟