blob: f5a854414c16699dc63e6a209a14148a724cb92b [file] [log] [blame]
Guido van Rossum7736b5b2008-01-15 21:44:53 +00001# Originally contributed by Sjoerd Mullender.
2# Significantly modified by Jeffrey Yasskin <jyasskin at gmail.com>.
3
Christian Heimes3feef612008-02-11 06:19:17 +00004"""Fraction, infinite-precision, real numbers."""
Guido van Rossum7736b5b2008-01-15 21:44:53 +00005
Mark Dickinson98127c32010-04-03 11:18:52 +00006from decimal import Decimal
Guido van Rossum7736b5b2008-01-15 21:44:53 +00007import math
8import numbers
9import operator
Christian Heimes587c2bf2008-01-19 16:21:02 +000010import re
Mark Dickinsondc787d22010-05-23 13:33:13 +000011import sys
Guido van Rossum7736b5b2008-01-15 21:44:53 +000012
Victor Stinner4691a2f2020-01-16 11:02:51 +010013__all__ = ['Fraction']
Guido van Rossum7736b5b2008-01-15 21:44:53 +000014
Guido van Rossum7736b5b2008-01-15 21:44:53 +000015
Mark Dickinsondc787d22010-05-23 13:33:13 +000016# Constants related to the hash implementation; hash(x) is based
17# on the reduction of x modulo the prime _PyHASH_MODULUS.
18_PyHASH_MODULUS = sys.hash_info.modulus
19# Value to be used for rationals that reduce to infinity modulo
20# _PyHASH_MODULUS.
21_PyHASH_INF = sys.hash_info.inf
Guido van Rossum7736b5b2008-01-15 21:44:53 +000022
Christian Heimes292d3512008-02-03 16:51:08 +000023_RATIONAL_FORMAT = re.compile(r"""
24 \A\s* # optional whitespace at the start, then
25 (?P<sign>[-+]?) # an optional sign, then
26 (?=\d|\.\d) # lookahead for digit or .digit
27 (?P<num>\d*) # numerator (possibly empty)
Mark Dickinsoncf63f2f2009-04-22 17:50:21 +000028 (?: # followed by
29 (?:/(?P<denom>\d+))? # an optional denominator
Christian Heimes292d3512008-02-03 16:51:08 +000030 | # or
Mark Dickinsoncf63f2f2009-04-22 17:50:21 +000031 (?:\.(?P<decimal>\d*))? # an optional fractional part
32 (?:E(?P<exp>[-+]?\d+))? # and optional exponent
33 )
Christian Heimes292d3512008-02-03 16:51:08 +000034 \s*\Z # and optional whitespace to finish
Mark Dickinsoncf63f2f2009-04-22 17:50:21 +000035""", re.VERBOSE | re.IGNORECASE)
Christian Heimes587c2bf2008-01-19 16:21:02 +000036
37
Christian Heimes3feef612008-02-11 06:19:17 +000038class Fraction(numbers.Rational):
Guido van Rossum7736b5b2008-01-15 21:44:53 +000039 """This class implements rational numbers.
40
Mark Dickinson98127c32010-04-03 11:18:52 +000041 In the two-argument form of the constructor, Fraction(8, 6) will
42 produce a rational number equivalent to 4/3. Both arguments must
43 be Rational. The numerator defaults to 0 and the denominator
44 defaults to 1 so that Fraction(3) == 3 and Fraction() == 0.
Guido van Rossum7736b5b2008-01-15 21:44:53 +000045
Mark Dickinson98127c32010-04-03 11:18:52 +000046 Fractions can also be constructed from:
47
48 - numeric strings similar to those accepted by the
49 float constructor (for example, '-2.3' or '1e10')
50
51 - strings of the form '123/456'
52
53 - float and Decimal instances
54
55 - other Rational instances (including integers)
Christian Heimes587c2bf2008-01-19 16:21:02 +000056
Guido van Rossum7736b5b2008-01-15 21:44:53 +000057 """
58
Christian Heimes400adb02008-02-01 08:12:03 +000059 __slots__ = ('_numerator', '_denominator')
Guido van Rossum7736b5b2008-01-15 21:44:53 +000060
Christian Heimes587c2bf2008-01-19 16:21:02 +000061 # We're immutable, so use __new__ not __init__
Mark Dickinson7caf9082016-08-23 16:16:52 +010062 def __new__(cls, numerator=0, denominator=None, *, _normalize=True):
Christian Heimes587c2bf2008-01-19 16:21:02 +000063 """Constructs a Rational.
64
Mark Dickinson98127c32010-04-03 11:18:52 +000065 Takes a string like '3/2' or '1.5', another Rational instance, a
66 numerator/denominator pair, or a float.
67
68 Examples
69 --------
70
71 >>> Fraction(10, -8)
72 Fraction(-5, 4)
73 >>> Fraction(Fraction(1, 7), 5)
74 Fraction(1, 35)
75 >>> Fraction(Fraction(1, 7), Fraction(2, 3))
76 Fraction(3, 14)
77 >>> Fraction('314')
78 Fraction(314, 1)
79 >>> Fraction('-35/4')
80 Fraction(-35, 4)
81 >>> Fraction('3.1415') # conversion from numeric string
82 Fraction(6283, 2000)
83 >>> Fraction('-47e-2') # string may include a decimal exponent
84 Fraction(-47, 100)
85 >>> Fraction(1.47) # direct construction from float (exact conversion)
86 Fraction(6620291452234629, 4503599627370496)
87 >>> Fraction(2.25)
88 Fraction(9, 4)
89 >>> Fraction(Decimal('1.47'))
90 Fraction(147, 100)
Christian Heimes587c2bf2008-01-19 16:21:02 +000091
92 """
Christian Heimes3feef612008-02-11 06:19:17 +000093 self = super(Fraction, cls).__new__(cls)
Christian Heimes587c2bf2008-01-19 16:21:02 +000094
Mark Dickinsond4d95f82009-04-24 14:06:19 +000095 if denominator is None:
Georg Brandl40f97352014-09-24 08:37:55 +020096 if type(numerator) is int:
97 self._numerator = numerator
98 self._denominator = 1
99 return self
100
101 elif isinstance(numerator, numbers.Rational):
Mark Dickinsond4d95f82009-04-24 14:06:19 +0000102 self._numerator = numerator.numerator
103 self._denominator = numerator.denominator
104 return self
105
Serhiy Storchaka0d250bc2015-12-29 22:34:23 +0200106 elif isinstance(numerator, (float, Decimal)):
107 # Exact conversion
108 self._numerator, self._denominator = numerator.as_integer_ratio()
Mark Dickinson98127c32010-04-03 11:18:52 +0000109 return self
110
Mark Dickinsond4d95f82009-04-24 14:06:19 +0000111 elif isinstance(numerator, str):
Christian Heimes587c2bf2008-01-19 16:21:02 +0000112 # Handle construction from strings.
Mark Dickinsoncf63f2f2009-04-22 17:50:21 +0000113 m = _RATIONAL_FORMAT.match(numerator)
Christian Heimes587c2bf2008-01-19 16:21:02 +0000114 if m is None:
Mark Dickinsoncf63f2f2009-04-22 17:50:21 +0000115 raise ValueError('Invalid literal for Fraction: %r' %
116 numerator)
117 numerator = int(m.group('num') or '0')
118 denom = m.group('denom')
119 if denom:
120 denominator = int(denom)
Christian Heimesaf98da12008-01-27 15:18:18 +0000121 else:
Mark Dickinsoncf63f2f2009-04-22 17:50:21 +0000122 denominator = 1
123 decimal = m.group('decimal')
124 if decimal:
125 scale = 10**len(decimal)
126 numerator = numerator * scale + int(decimal)
127 denominator *= scale
128 exp = m.group('exp')
129 if exp:
130 exp = int(exp)
131 if exp >= 0:
132 numerator *= 10**exp
133 else:
134 denominator *= 10**-exp
Christian Heimes587c2bf2008-01-19 16:21:02 +0000135 if m.group('sign') == '-':
136 numerator = -numerator
137
Mark Dickinsond4d95f82009-04-24 14:06:19 +0000138 else:
139 raise TypeError("argument should be a string "
140 "or a Rational instance")
141
Georg Brandl40f97352014-09-24 08:37:55 +0200142 elif type(numerator) is int is type(denominator):
Serhiy Storchaka48e47aa2015-05-13 00:19:51 +0300143 pass # *very* normal case
Georg Brandl40f97352014-09-24 08:37:55 +0200144
Mark Dickinsond4d95f82009-04-24 14:06:19 +0000145 elif (isinstance(numerator, numbers.Rational) and
146 isinstance(denominator, numbers.Rational)):
147 numerator, denominator = (
148 numerator.numerator * denominator.denominator,
149 denominator.numerator * numerator.denominator
150 )
151 else:
152 raise TypeError("both arguments should be "
153 "Rational instances")
Guido van Rossum7736b5b2008-01-15 21:44:53 +0000154
Guido van Rossum7736b5b2008-01-15 21:44:53 +0000155 if denominator == 0:
Christian Heimes3feef612008-02-11 06:19:17 +0000156 raise ZeroDivisionError('Fraction(%s, 0)' % numerator)
Mark Dickinson3c286e22014-04-05 09:29:00 +0100157 if _normalize:
Serhiy Storchaka48e47aa2015-05-13 00:19:51 +0300158 if type(numerator) is int is type(denominator):
159 # *very* normal case
160 g = math.gcd(numerator, denominator)
161 if denominator < 0:
162 g = -g
163 else:
164 g = _gcd(numerator, denominator)
Mark Dickinson3c286e22014-04-05 09:29:00 +0100165 numerator //= g
166 denominator //= g
167 self._numerator = numerator
168 self._denominator = denominator
Christian Heimes587c2bf2008-01-19 16:21:02 +0000169 return self
Guido van Rossum7736b5b2008-01-15 21:44:53 +0000170
171 @classmethod
172 def from_float(cls, f):
Christian Heimes587c2bf2008-01-19 16:21:02 +0000173 """Converts a finite float to a rational number, exactly.
174
Christian Heimes3feef612008-02-11 06:19:17 +0000175 Beware that Fraction.from_float(0.3) != Fraction(3, 10).
Christian Heimes587c2bf2008-01-19 16:21:02 +0000176
177 """
Georg Brandl2ee470f2008-07-16 12:55:28 +0000178 if isinstance(f, numbers.Integral):
Georg Brandl3a9b0622009-01-03 22:07:57 +0000179 return cls(f)
Georg Brandl2ee470f2008-07-16 12:55:28 +0000180 elif not isinstance(f, float):
Guido van Rossum7736b5b2008-01-15 21:44:53 +0000181 raise TypeError("%s.from_float() only takes floats, not %r (%s)" %
182 (cls.__name__, f, type(f).__name__))
Christian Heimes26855632008-01-27 23:50:43 +0000183 return cls(*f.as_integer_ratio())
Guido van Rossum7736b5b2008-01-15 21:44:53 +0000184
Christian Heimes587c2bf2008-01-19 16:21:02 +0000185 @classmethod
186 def from_decimal(cls, dec):
187 """Converts a finite Decimal instance to a rational number, exactly."""
188 from decimal import Decimal
Georg Brandl2ee470f2008-07-16 12:55:28 +0000189 if isinstance(dec, numbers.Integral):
190 dec = Decimal(int(dec))
191 elif not isinstance(dec, Decimal):
Christian Heimes587c2bf2008-01-19 16:21:02 +0000192 raise TypeError(
193 "%s.from_decimal() only takes Decimals, not %r (%s)" %
194 (cls.__name__, dec, type(dec).__name__))
Serhiy Storchaka0d250bc2015-12-29 22:34:23 +0200195 return cls(*dec.as_integer_ratio())
Christian Heimes587c2bf2008-01-19 16:21:02 +0000196
Raymond Hettingerf03b4c82019-08-11 14:40:59 -0700197 def as_integer_ratio(self):
198 """Return the integer ratio as a tuple.
199
200 Return a tuple of two integers, whose ratio is equal to the
201 Fraction and with a positive denominator.
202 """
203 return (self._numerator, self._denominator)
204
Christian Heimes68f5fbe2008-02-14 08:27:37 +0000205 def limit_denominator(self, max_denominator=1000000):
206 """Closest Fraction to self with denominator at most max_denominator.
Christian Heimesbbffeb62008-01-24 09:42:52 +0000207
Christian Heimes68f5fbe2008-02-14 08:27:37 +0000208 >>> Fraction('3.141592653589793').limit_denominator(10)
209 Fraction(22, 7)
210 >>> Fraction('3.141592653589793').limit_denominator(100)
211 Fraction(311, 99)
Mark Dickinsondfb15622009-11-23 16:27:17 +0000212 >>> Fraction(4321, 8765).limit_denominator(10000)
213 Fraction(4321, 8765)
Christian Heimesbbffeb62008-01-24 09:42:52 +0000214
Christian Heimes68f5fbe2008-02-14 08:27:37 +0000215 """
216 # Algorithm notes: For any real number x, define a *best upper
217 # approximation* to x to be a rational number p/q such that:
218 #
219 # (1) p/q >= x, and
220 # (2) if p/q > r/s >= x then s > q, for any rational r/s.
221 #
222 # Define *best lower approximation* similarly. Then it can be
223 # proved that a rational number is a best upper or lower
224 # approximation to x if, and only if, it is a convergent or
225 # semiconvergent of the (unique shortest) continued fraction
226 # associated to x.
227 #
228 # To find a best rational approximation with denominator <= M,
229 # we find the best upper and lower approximations with
230 # denominator <= M and take whichever of these is closer to x.
231 # In the event of a tie, the bound with smaller denominator is
232 # chosen. If both denominators are equal (which can happen
233 # only when max_denominator == 1 and self is midway between
234 # two integers) the lower bound---i.e., the floor of self, is
235 # taken.
236
237 if max_denominator < 1:
238 raise ValueError("max_denominator should be at least 1")
239 if self._denominator <= max_denominator:
240 return Fraction(self)
241
242 p0, q0, p1, q1 = 0, 1, 1, 0
243 n, d = self._numerator, self._denominator
244 while True:
245 a = n//d
246 q2 = q0+a*q1
247 if q2 > max_denominator:
Christian Heimesbbffeb62008-01-24 09:42:52 +0000248 break
Christian Heimes68f5fbe2008-02-14 08:27:37 +0000249 p0, q0, p1, q1 = p1, q1, p0+a*p1, q2
250 n, d = d, n-a*d
251
252 k = (max_denominator-q0)//q1
253 bound1 = Fraction(p0+k*p1, q0+k*q1)
254 bound2 = Fraction(p1, q1)
255 if abs(bound2 - self) <= abs(bound1-self):
256 return bound2
257 else:
258 return bound1
Christian Heimesbbffeb62008-01-24 09:42:52 +0000259
Christian Heimes400adb02008-02-01 08:12:03 +0000260 @property
261 def numerator(a):
262 return a._numerator
263
264 @property
265 def denominator(a):
266 return a._denominator
267
Guido van Rossum7736b5b2008-01-15 21:44:53 +0000268 def __repr__(self):
269 """repr(self)"""
Serhiy Storchaka465e60e2014-07-25 23:36:00 +0300270 return '%s(%s, %s)' % (self.__class__.__name__,
271 self._numerator, self._denominator)
Guido van Rossum7736b5b2008-01-15 21:44:53 +0000272
273 def __str__(self):
274 """str(self)"""
Christian Heimes68f5fbe2008-02-14 08:27:37 +0000275 if self._denominator == 1:
276 return str(self._numerator)
Guido van Rossum7736b5b2008-01-15 21:44:53 +0000277 else:
Christian Heimes68f5fbe2008-02-14 08:27:37 +0000278 return '%s/%s' % (self._numerator, self._denominator)
Guido van Rossum7736b5b2008-01-15 21:44:53 +0000279
280 def _operator_fallbacks(monomorphic_operator, fallback_operator):
281 """Generates forward and reverse operators given a purely-rational
282 operator and a function from the operator module.
283
284 Use this like:
285 __op__, __rop__ = _operator_fallbacks(just_rational_op, operator.op)
286
Christian Heimes7b3ce6a2008-01-31 14:31:45 +0000287 In general, we want to implement the arithmetic operations so
288 that mixed-mode operations either call an implementation whose
289 author knew about the types of both arguments, or convert both
290 to the nearest built in type and do the operation there. In
Christian Heimes3feef612008-02-11 06:19:17 +0000291 Fraction, that means that we define __add__ and __radd__ as:
Christian Heimes7b3ce6a2008-01-31 14:31:45 +0000292
293 def __add__(self, other):
Christian Heimes400adb02008-02-01 08:12:03 +0000294 # Both types have numerators/denominator attributes,
295 # so do the operation directly
Christian Heimes3feef612008-02-11 06:19:17 +0000296 if isinstance(other, (int, Fraction)):
297 return Fraction(self.numerator * other.denominator +
Christian Heimes7b3ce6a2008-01-31 14:31:45 +0000298 other.numerator * self.denominator,
299 self.denominator * other.denominator)
Christian Heimes400adb02008-02-01 08:12:03 +0000300 # float and complex don't have those operations, but we
301 # know about those types, so special case them.
Christian Heimes7b3ce6a2008-01-31 14:31:45 +0000302 elif isinstance(other, float):
303 return float(self) + other
304 elif isinstance(other, complex):
305 return complex(self) + other
Christian Heimes400adb02008-02-01 08:12:03 +0000306 # Let the other type take over.
307 return NotImplemented
Christian Heimes7b3ce6a2008-01-31 14:31:45 +0000308
309 def __radd__(self, other):
310 # radd handles more types than add because there's
311 # nothing left to fall back to.
Christian Heimes3feef612008-02-11 06:19:17 +0000312 if isinstance(other, numbers.Rational):
313 return Fraction(self.numerator * other.denominator +
Christian Heimes7b3ce6a2008-01-31 14:31:45 +0000314 other.numerator * self.denominator,
315 self.denominator * other.denominator)
316 elif isinstance(other, Real):
317 return float(other) + float(self)
318 elif isinstance(other, Complex):
319 return complex(other) + complex(self)
Christian Heimes400adb02008-02-01 08:12:03 +0000320 return NotImplemented
Christian Heimes7b3ce6a2008-01-31 14:31:45 +0000321
322
323 There are 5 different cases for a mixed-type addition on
Christian Heimes3feef612008-02-11 06:19:17 +0000324 Fraction. I'll refer to all of the above code that doesn't
325 refer to Fraction, float, or complex as "boilerplate". 'r'
326 will be an instance of Fraction, which is a subtype of
327 Rational (r : Fraction <: Rational), and b : B <:
Christian Heimes7b3ce6a2008-01-31 14:31:45 +0000328 Complex. The first three involve 'r + b':
329
Christian Heimes3feef612008-02-11 06:19:17 +0000330 1. If B <: Fraction, int, float, or complex, we handle
Christian Heimes7b3ce6a2008-01-31 14:31:45 +0000331 that specially, and all is well.
Christian Heimes3feef612008-02-11 06:19:17 +0000332 2. If Fraction falls back to the boilerplate code, and it
Christian Heimes7b3ce6a2008-01-31 14:31:45 +0000333 were to return a value from __add__, we'd miss the
334 possibility that B defines a more intelligent __radd__,
335 so the boilerplate should return NotImplemented from
Christian Heimes3feef612008-02-11 06:19:17 +0000336 __add__. In particular, we don't handle Rational
Christian Heimes7b3ce6a2008-01-31 14:31:45 +0000337 here, even though we could get an exact answer, in case
338 the other type wants to do something special.
Christian Heimes3feef612008-02-11 06:19:17 +0000339 3. If B <: Fraction, Python tries B.__radd__ before
340 Fraction.__add__. This is ok, because it was
341 implemented with knowledge of Fraction, so it can
Christian Heimes7b3ce6a2008-01-31 14:31:45 +0000342 handle those instances before delegating to Real or
343 Complex.
344
345 The next two situations describe 'b + r'. We assume that b
Christian Heimes3feef612008-02-11 06:19:17 +0000346 didn't know about Fraction in its implementation, and that it
Christian Heimes7b3ce6a2008-01-31 14:31:45 +0000347 uses similar boilerplate code:
348
Christian Heimes3feef612008-02-11 06:19:17 +0000349 4. If B <: Rational, then __radd_ converts both to the
Christian Heimes7b3ce6a2008-01-31 14:31:45 +0000350 builtin rational type (hey look, that's us) and
351 proceeds.
352 5. Otherwise, __radd__ tries to find the nearest common
353 base ABC, and fall back to its builtin type. Since this
354 class doesn't subclass a concrete type, there's no
355 implementation to fall back to, so we need to try as
356 hard as possible to return an actual value, or the user
357 will get a TypeError.
358
Guido van Rossum7736b5b2008-01-15 21:44:53 +0000359 """
360 def forward(a, b):
Christian Heimes3feef612008-02-11 06:19:17 +0000361 if isinstance(b, (int, Fraction)):
Guido van Rossum7736b5b2008-01-15 21:44:53 +0000362 return monomorphic_operator(a, b)
363 elif isinstance(b, float):
364 return fallback_operator(float(a), b)
365 elif isinstance(b, complex):
366 return fallback_operator(complex(a), b)
367 else:
368 return NotImplemented
369 forward.__name__ = '__' + fallback_operator.__name__ + '__'
370 forward.__doc__ = monomorphic_operator.__doc__
371
372 def reverse(b, a):
Christian Heimes3feef612008-02-11 06:19:17 +0000373 if isinstance(a, numbers.Rational):
Guido van Rossum7736b5b2008-01-15 21:44:53 +0000374 # Includes ints.
375 return monomorphic_operator(a, b)
376 elif isinstance(a, numbers.Real):
377 return fallback_operator(float(a), float(b))
378 elif isinstance(a, numbers.Complex):
379 return fallback_operator(complex(a), complex(b))
380 else:
381 return NotImplemented
382 reverse.__name__ = '__r' + fallback_operator.__name__ + '__'
383 reverse.__doc__ = monomorphic_operator.__doc__
384
385 return forward, reverse
386
387 def _add(a, b):
388 """a + b"""
Georg Brandl40f97352014-09-24 08:37:55 +0200389 da, db = a.denominator, b.denominator
390 return Fraction(a.numerator * db + b.numerator * da,
391 da * db)
Guido van Rossum7736b5b2008-01-15 21:44:53 +0000392
393 __add__, __radd__ = _operator_fallbacks(_add, operator.add)
394
395 def _sub(a, b):
396 """a - b"""
Georg Brandl40f97352014-09-24 08:37:55 +0200397 da, db = a.denominator, b.denominator
398 return Fraction(a.numerator * db - b.numerator * da,
399 da * db)
Guido van Rossum7736b5b2008-01-15 21:44:53 +0000400
401 __sub__, __rsub__ = _operator_fallbacks(_sub, operator.sub)
402
403 def _mul(a, b):
404 """a * b"""
Christian Heimes3feef612008-02-11 06:19:17 +0000405 return Fraction(a.numerator * b.numerator, a.denominator * b.denominator)
Guido van Rossum7736b5b2008-01-15 21:44:53 +0000406
407 __mul__, __rmul__ = _operator_fallbacks(_mul, operator.mul)
408
409 def _div(a, b):
410 """a / b"""
Christian Heimes3feef612008-02-11 06:19:17 +0000411 return Fraction(a.numerator * b.denominator,
Guido van Rossum7736b5b2008-01-15 21:44:53 +0000412 a.denominator * b.numerator)
413
414 __truediv__, __rtruediv__ = _operator_fallbacks(_div, operator.truediv)
Guido van Rossum7736b5b2008-01-15 21:44:53 +0000415
Elias Zamaria393f1ff2018-08-26 23:59:28 -0700416 def _floordiv(a, b):
Guido van Rossum7736b5b2008-01-15 21:44:53 +0000417 """a // b"""
Stefan Behnel3a374e02019-01-02 13:22:06 +0100418 return (a.numerator * b.denominator) // (a.denominator * b.numerator)
Guido van Rossum7736b5b2008-01-15 21:44:53 +0000419
Elias Zamaria393f1ff2018-08-26 23:59:28 -0700420 __floordiv__, __rfloordiv__ = _operator_fallbacks(_floordiv, operator.floordiv)
Guido van Rossum7736b5b2008-01-15 21:44:53 +0000421
Stefan Behnel3a374e02019-01-02 13:22:06 +0100422 def _divmod(a, b):
423 """(a // b, a % b)"""
424 da, db = a.denominator, b.denominator
425 div, n_mod = divmod(a.numerator * db, da * b.numerator)
426 return div, Fraction(n_mod, da * db)
427
428 __divmod__, __rdivmod__ = _operator_fallbacks(_divmod, divmod)
429
Elias Zamaria393f1ff2018-08-26 23:59:28 -0700430 def _mod(a, b):
Christian Heimes969fe572008-01-25 11:23:10 +0000431 """a % b"""
Stefan Behnel3a374e02019-01-02 13:22:06 +0100432 da, db = a.denominator, b.denominator
433 return Fraction((a.numerator * db) % (b.numerator * da), da * db)
Guido van Rossum7736b5b2008-01-15 21:44:53 +0000434
Elias Zamaria393f1ff2018-08-26 23:59:28 -0700435 __mod__, __rmod__ = _operator_fallbacks(_mod, operator.mod)
Guido van Rossum7736b5b2008-01-15 21:44:53 +0000436
437 def __pow__(a, b):
438 """a ** b
439
440 If b is not an integer, the result will be a float or complex
441 since roots are generally irrational. If b is an integer, the
442 result will be rational.
443
444 """
Christian Heimes3feef612008-02-11 06:19:17 +0000445 if isinstance(b, numbers.Rational):
Guido van Rossum7736b5b2008-01-15 21:44:53 +0000446 if b.denominator == 1:
447 power = b.numerator
448 if power >= 0:
Christian Heimes68f5fbe2008-02-14 08:27:37 +0000449 return Fraction(a._numerator ** power,
Mark Dickinson3c286e22014-04-05 09:29:00 +0100450 a._denominator ** power,
451 _normalize=False)
Mark Dickinson84479652016-08-22 10:50:53 +0100452 elif a._numerator >= 0:
Christian Heimes68f5fbe2008-02-14 08:27:37 +0000453 return Fraction(a._denominator ** -power,
Mark Dickinson3c286e22014-04-05 09:29:00 +0100454 a._numerator ** -power,
455 _normalize=False)
Mark Dickinson84479652016-08-22 10:50:53 +0100456 else:
457 return Fraction((-a._denominator) ** -power,
458 (-a._numerator) ** -power,
459 _normalize=False)
Guido van Rossum7736b5b2008-01-15 21:44:53 +0000460 else:
461 # A fractional power will generally produce an
462 # irrational number.
463 return float(a) ** float(b)
464 else:
465 return float(a) ** b
466
467 def __rpow__(b, a):
468 """a ** b"""
Christian Heimes68f5fbe2008-02-14 08:27:37 +0000469 if b._denominator == 1 and b._numerator >= 0:
Guido van Rossum7736b5b2008-01-15 21:44:53 +0000470 # If a is an int, keep it that way if possible.
Christian Heimes68f5fbe2008-02-14 08:27:37 +0000471 return a ** b._numerator
Guido van Rossum7736b5b2008-01-15 21:44:53 +0000472
Christian Heimes3feef612008-02-11 06:19:17 +0000473 if isinstance(a, numbers.Rational):
474 return Fraction(a.numerator, a.denominator) ** b
Guido van Rossum7736b5b2008-01-15 21:44:53 +0000475
Christian Heimes68f5fbe2008-02-14 08:27:37 +0000476 if b._denominator == 1:
477 return a ** b._numerator
Guido van Rossum7736b5b2008-01-15 21:44:53 +0000478
479 return a ** float(b)
480
481 def __pos__(a):
Christian Heimes3feef612008-02-11 06:19:17 +0000482 """+a: Coerces a subclass instance to Fraction"""
Mark Dickinson3c286e22014-04-05 09:29:00 +0100483 return Fraction(a._numerator, a._denominator, _normalize=False)
Guido van Rossum7736b5b2008-01-15 21:44:53 +0000484
485 def __neg__(a):
486 """-a"""
Mark Dickinson3c286e22014-04-05 09:29:00 +0100487 return Fraction(-a._numerator, a._denominator, _normalize=False)
Guido van Rossum7736b5b2008-01-15 21:44:53 +0000488
489 def __abs__(a):
490 """abs(a)"""
Mark Dickinson3c286e22014-04-05 09:29:00 +0100491 return Fraction(abs(a._numerator), a._denominator, _normalize=False)
Guido van Rossum7736b5b2008-01-15 21:44:53 +0000492
493 def __trunc__(a):
494 """trunc(a)"""
Christian Heimes68f5fbe2008-02-14 08:27:37 +0000495 if a._numerator < 0:
496 return -(-a._numerator // a._denominator)
Guido van Rossum7736b5b2008-01-15 21:44:53 +0000497 else:
Christian Heimes68f5fbe2008-02-14 08:27:37 +0000498 return a._numerator // a._denominator
Guido van Rossum7736b5b2008-01-15 21:44:53 +0000499
500 def __floor__(a):
Jakub Molinskia9a28802019-04-15 14:37:04 +0200501 """math.floor(a)"""
Guido van Rossum7736b5b2008-01-15 21:44:53 +0000502 return a.numerator // a.denominator
503
504 def __ceil__(a):
Jakub Molinskia9a28802019-04-15 14:37:04 +0200505 """math.ceil(a)"""
Guido van Rossum7736b5b2008-01-15 21:44:53 +0000506 # The negations cleverly convince floordiv to return the ceiling.
507 return -(-a.numerator // a.denominator)
508
509 def __round__(self, ndigits=None):
Jakub Molinskia9a28802019-04-15 14:37:04 +0200510 """round(self, ndigits)
Guido van Rossum7736b5b2008-01-15 21:44:53 +0000511
512 Rounds half toward even.
513 """
514 if ndigits is None:
515 floor, remainder = divmod(self.numerator, self.denominator)
516 if remainder * 2 < self.denominator:
517 return floor
518 elif remainder * 2 > self.denominator:
519 return floor + 1
520 # Deal with the half case:
521 elif floor % 2 == 0:
522 return floor
523 else:
524 return floor + 1
525 shift = 10**abs(ndigits)
526 # See _operator_fallbacks.forward to check that the results of
Christian Heimes3feef612008-02-11 06:19:17 +0000527 # these operations will always be Fraction and therefore have
Jeffrey Yasskin9893de12008-01-17 07:36:30 +0000528 # round().
Guido van Rossum7736b5b2008-01-15 21:44:53 +0000529 if ndigits > 0:
Christian Heimes3feef612008-02-11 06:19:17 +0000530 return Fraction(round(self * shift), shift)
Guido van Rossum7736b5b2008-01-15 21:44:53 +0000531 else:
Christian Heimes3feef612008-02-11 06:19:17 +0000532 return Fraction(round(self / shift) * shift)
Guido van Rossum7736b5b2008-01-15 21:44:53 +0000533
534 def __hash__(self):
Mark Dickinsonfec66202010-11-13 10:27:38 +0000535 """hash(self)"""
Guido van Rossum7736b5b2008-01-15 21:44:53 +0000536
Raymond Hettingerf3cb68f2019-08-15 20:58:26 -0700537 # To make sure that the hash of a Fraction agrees with the hash
538 # of a numerically equal integer, float or Decimal instance, we
539 # follow the rules for numeric hashes outlined in the
540 # documentation. (See library docs, 'Built-in Types').
Mark Dickinsondc787d22010-05-23 13:33:13 +0000541
Raymond Hettingerf3cb68f2019-08-15 20:58:26 -0700542 try:
543 dinv = pow(self._denominator, -1, _PyHASH_MODULUS)
544 except ValueError:
Tim Peters29bb2272019-08-16 21:09:16 -0500545 # ValueError means there is no modular inverse.
Mark Dickinsondc787d22010-05-23 13:33:13 +0000546 hash_ = _PyHASH_INF
Guido van Rossum7736b5b2008-01-15 21:44:53 +0000547 else:
Tim Peters29bb2272019-08-16 21:09:16 -0500548 # The general algorithm now specifies that the absolute value of
549 # the hash is
550 # (|N| * dinv) % P
551 # where N is self._numerator and P is _PyHASH_MODULUS. That's
552 # optimized here in two ways: first, for a non-negative int i,
553 # hash(i) == i % P, but the int hash implementation doesn't need
554 # to divide, and is faster than doing % P explicitly. So we do
555 # hash(|N| * dinv)
556 # instead. Second, N is unbounded, so its product with dinv may
557 # be arbitrarily expensive to compute. The final answer is the
558 # same if we use the bounded |N| % P instead, which can again
559 # be done with an int hash() call. If 0 <= i < P, hash(i) == i,
560 # so this nested hash() call wastes a bit of time making a
561 # redundant copy when |N| < P, but can save an arbitrarily large
562 # amount of computation for large |N|.
563 hash_ = hash(hash(abs(self._numerator)) * dinv)
Raymond Hettingerf3cb68f2019-08-15 20:58:26 -0700564 result = hash_ if self._numerator >= 0 else -hash_
Mark Dickinsonfec66202010-11-13 10:27:38 +0000565 return -2 if result == -1 else result
Guido van Rossum7736b5b2008-01-15 21:44:53 +0000566
567 def __eq__(a, b):
568 """a == b"""
Georg Brandl40f97352014-09-24 08:37:55 +0200569 if type(b) is int:
570 return a._numerator == b and a._denominator == 1
Christian Heimes3feef612008-02-11 06:19:17 +0000571 if isinstance(b, numbers.Rational):
Christian Heimes68f5fbe2008-02-14 08:27:37 +0000572 return (a._numerator == b.numerator and
573 a._denominator == b.denominator)
Guido van Rossum7736b5b2008-01-15 21:44:53 +0000574 if isinstance(b, numbers.Complex) and b.imag == 0:
575 b = b.real
576 if isinstance(b, float):
Mark Dickinson85424c92009-07-18 14:41:42 +0000577 if math.isnan(b) or math.isinf(b):
578 # comparisons with an infinity or nan should behave in
579 # the same way for any finite a, so treat a as zero.
580 return 0.0 == b
581 else:
582 return a == a.from_float(b)
Guido van Rossum7736b5b2008-01-15 21:44:53 +0000583 else:
Mark Dickinson85424c92009-07-18 14:41:42 +0000584 # Since a doesn't know how to compare with b, let's give b
585 # a chance to compare itself with a.
586 return NotImplemented
Guido van Rossum7736b5b2008-01-15 21:44:53 +0000587
Mark Dickinson85424c92009-07-18 14:41:42 +0000588 def _richcmp(self, other, op):
589 """Helper for comparison operators, for internal use only.
Guido van Rossum7736b5b2008-01-15 21:44:53 +0000590
Mark Dickinson85424c92009-07-18 14:41:42 +0000591 Implement comparison between a Rational instance `self`, and
592 either another Rational instance or a float `other`. If
593 `other` is not a Rational instance or a float, return
594 NotImplemented. `op` should be one of the six standard
595 comparison operators.
Guido van Rossum7736b5b2008-01-15 21:44:53 +0000596
597 """
Mark Dickinson85424c92009-07-18 14:41:42 +0000598 # convert other to a Rational instance where reasonable.
599 if isinstance(other, numbers.Rational):
600 return op(self._numerator * other.denominator,
601 self._denominator * other.numerator)
Mark Dickinson85424c92009-07-18 14:41:42 +0000602 if isinstance(other, float):
603 if math.isnan(other) or math.isinf(other):
604 return op(0.0, other)
605 else:
606 return op(self, self.from_float(other))
607 else:
Guido van Rossum7736b5b2008-01-15 21:44:53 +0000608 return NotImplemented
Guido van Rossum7736b5b2008-01-15 21:44:53 +0000609
610 def __lt__(a, b):
611 """a < b"""
Mark Dickinson85424c92009-07-18 14:41:42 +0000612 return a._richcmp(b, operator.lt)
Guido van Rossum7736b5b2008-01-15 21:44:53 +0000613
614 def __gt__(a, b):
615 """a > b"""
Mark Dickinson85424c92009-07-18 14:41:42 +0000616 return a._richcmp(b, operator.gt)
Guido van Rossum7736b5b2008-01-15 21:44:53 +0000617
618 def __le__(a, b):
619 """a <= b"""
Mark Dickinson85424c92009-07-18 14:41:42 +0000620 return a._richcmp(b, operator.le)
Guido van Rossum7736b5b2008-01-15 21:44:53 +0000621
622 def __ge__(a, b):
623 """a >= b"""
Mark Dickinson85424c92009-07-18 14:41:42 +0000624 return a._richcmp(b, operator.ge)
Guido van Rossum7736b5b2008-01-15 21:44:53 +0000625
626 def __bool__(a):
627 """a != 0"""
Sebastian Berg427c84f2020-02-06 06:54:05 -0800628 # bpo-39274: Use bool() because (a._numerator != 0) can return an
629 # object which is not a bool.
630 return bool(a._numerator)
Christian Heimes969fe572008-01-25 11:23:10 +0000631
632 # support for pickling, copy, and deepcopy
633
634 def __reduce__(self):
635 return (self.__class__, (str(self),))
636
637 def __copy__(self):
Christian Heimes3feef612008-02-11 06:19:17 +0000638 if type(self) == Fraction:
Christian Heimes969fe572008-01-25 11:23:10 +0000639 return self # I'm immutable; therefore I am my own clone
Christian Heimes68f5fbe2008-02-14 08:27:37 +0000640 return self.__class__(self._numerator, self._denominator)
Christian Heimes969fe572008-01-25 11:23:10 +0000641
642 def __deepcopy__(self, memo):
Christian Heimes3feef612008-02-11 06:19:17 +0000643 if type(self) == Fraction:
Christian Heimes969fe572008-01-25 11:23:10 +0000644 return self # My components are also immutable
Christian Heimes68f5fbe2008-02-14 08:27:37 +0000645 return self.__class__(self._numerator, self._denominator)