blob: c22137e8909b7f75f0b5bd6d3f6b58734c982ee0 [file] [log] [blame]
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00001# Copyright (c) 2004 Python Software Foundation.
2# All rights reserved.
3
4# Written by Eric Price <eprice at tjhsst.edu>
5# and Facundo Batista <facundo at taniquetil.com.ar>
6# and Raymond Hettinger <python at rcn.com>
Fred Drake1f34eb12004-07-01 14:28:36 +00007# and Aahz <aahz at pobox.com>
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00008# and Tim Peters
9
Raymond Hettinger27dbcf22004-08-19 22:39:55 +000010# This module is currently Py2.3 compatible and should be kept that way
11# unless a major compelling advantage arises. IOW, 2.3 compatibility is
12# strongly preferred, but not guaranteed.
13
14# Also, this module should be kept in sync with the latest updates of
15# the IBM specification as it evolves. Those updates will be treated
16# as bug fixes (deviation from the spec is a compatibility, usability
17# bug) and will be backported. At this point the spec is stabilizing
18# and the updates are becoming fewer, smaller, and less significant.
Raymond Hettinger7c85fa42004-07-01 11:01:35 +000019
Raymond Hettinger7c85fa42004-07-01 11:01:35 +000020"""
21This is a Py2.3 implementation of decimal floating point arithmetic based on
22the General Decimal Arithmetic Specification:
23
24 www2.hursley.ibm.com/decimal/decarith.html
25
Raymond Hettinger0ea241e2004-07-04 13:53:24 +000026and IEEE standard 854-1987:
Raymond Hettinger7c85fa42004-07-01 11:01:35 +000027
28 www.cs.berkeley.edu/~ejr/projects/754/private/drafts/854-1987/dir.html
29
Raymond Hettinger7c85fa42004-07-01 11:01:35 +000030Decimal floating point has finite precision with arbitrarily large bounds.
31
Facundo Batista59c58842007-04-10 12:58:45 +000032The purpose of this module is to support arithmetic using familiar
33"schoolhouse" rules and to avoid some of the tricky representation
Raymond Hettinger7c85fa42004-07-01 11:01:35 +000034issues associated with binary floating point. The package is especially
35useful for financial applications or for contexts where users have
36expectations that are at odds with binary floating point (for instance,
37in binary floating point, 1.00 % 0.1 gives 0.09999999999999995 instead
38of the expected Decimal("0.00") returned by decimal floating point).
39
40Here are some examples of using the decimal module:
41
42>>> from decimal import *
Raymond Hettingerbd7f76d2004-07-08 00:49:18 +000043>>> setcontext(ExtendedContext)
Raymond Hettinger7c85fa42004-07-01 11:01:35 +000044>>> Decimal(0)
45Decimal("0")
46>>> Decimal("1")
47Decimal("1")
48>>> Decimal("-.0123")
49Decimal("-0.0123")
50>>> Decimal(123456)
51Decimal("123456")
52>>> Decimal("123.45e12345678901234567890")
53Decimal("1.2345E+12345678901234567892")
54>>> Decimal("1.33") + Decimal("1.27")
55Decimal("2.60")
56>>> Decimal("12.34") + Decimal("3.87") - Decimal("18.41")
57Decimal("-2.20")
58>>> dig = Decimal(1)
59>>> print dig / Decimal(3)
600.333333333
61>>> getcontext().prec = 18
62>>> print dig / Decimal(3)
630.333333333333333333
64>>> print dig.sqrt()
651
66>>> print Decimal(3).sqrt()
671.73205080756887729
68>>> print Decimal(3) ** 123
694.85192780976896427E+58
70>>> inf = Decimal(1) / Decimal(0)
71>>> print inf
72Infinity
73>>> neginf = Decimal(-1) / Decimal(0)
74>>> print neginf
75-Infinity
76>>> print neginf + inf
77NaN
78>>> print neginf * inf
79-Infinity
80>>> print dig / 0
81Infinity
Raymond Hettingerbf440692004-07-10 14:14:37 +000082>>> getcontext().traps[DivisionByZero] = 1
Raymond Hettinger7c85fa42004-07-01 11:01:35 +000083>>> print dig / 0
84Traceback (most recent call last):
85 ...
86 ...
87 ...
88DivisionByZero: x / 0
89>>> c = Context()
Raymond Hettingerbf440692004-07-10 14:14:37 +000090>>> c.traps[InvalidOperation] = 0
Raymond Hettinger5aa478b2004-07-09 10:02:53 +000091>>> print c.flags[InvalidOperation]
Raymond Hettinger7c85fa42004-07-01 11:01:35 +0000920
93>>> c.divide(Decimal(0), Decimal(0))
94Decimal("NaN")
Raymond Hettingerbf440692004-07-10 14:14:37 +000095>>> c.traps[InvalidOperation] = 1
Raymond Hettinger5aa478b2004-07-09 10:02:53 +000096>>> print c.flags[InvalidOperation]
Raymond Hettinger7c85fa42004-07-01 11:01:35 +0000971
Raymond Hettinger5aa478b2004-07-09 10:02:53 +000098>>> c.flags[InvalidOperation] = 0
99>>> print c.flags[InvalidOperation]
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00001000
101>>> print c.divide(Decimal(0), Decimal(0))
102Traceback (most recent call last):
103 ...
104 ...
105 ...
Raymond Hettinger5aa478b2004-07-09 10:02:53 +0000106InvalidOperation: 0 / 0
107>>> print c.flags[InvalidOperation]
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00001081
Raymond Hettinger5aa478b2004-07-09 10:02:53 +0000109>>> c.flags[InvalidOperation] = 0
Raymond Hettingerbf440692004-07-10 14:14:37 +0000110>>> c.traps[InvalidOperation] = 0
Raymond Hettinger7c85fa42004-07-01 11:01:35 +0000111>>> print c.divide(Decimal(0), Decimal(0))
112NaN
Raymond Hettinger5aa478b2004-07-09 10:02:53 +0000113>>> print c.flags[InvalidOperation]
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00001141
115>>>
116"""
117
118__all__ = [
119 # Two major classes
120 'Decimal', 'Context',
121
122 # Contexts
Raymond Hettinger9ec3e3b2004-07-03 13:48:56 +0000123 'DefaultContext', 'BasicContext', 'ExtendedContext',
Raymond Hettinger7c85fa42004-07-01 11:01:35 +0000124
125 # Exceptions
Raymond Hettingerd87ac8f2004-07-09 10:52:54 +0000126 'DecimalException', 'Clamped', 'InvalidOperation', 'DivisionByZero',
127 'Inexact', 'Rounded', 'Subnormal', 'Overflow', 'Underflow',
Raymond Hettinger7c85fa42004-07-01 11:01:35 +0000128
Raymond Hettinger7c85fa42004-07-01 11:01:35 +0000129 # Constants for use in setting up contexts
130 'ROUND_DOWN', 'ROUND_HALF_UP', 'ROUND_HALF_EVEN', 'ROUND_CEILING',
131 'ROUND_FLOOR', 'ROUND_UP', 'ROUND_HALF_DOWN',
Raymond Hettinger7c85fa42004-07-01 11:01:35 +0000132
133 # Functions for manipulating contexts
Nick Coghlan8b6999b2006-08-31 12:00:43 +0000134 'setcontext', 'getcontext', 'localcontext'
Raymond Hettinger7c85fa42004-07-01 11:01:35 +0000135]
136
Raymond Hettingereb260842005-06-07 18:52:34 +0000137import copy as _copy
Raymond Hettinger7c85fa42004-07-01 11:01:35 +0000138
Facundo Batista59c58842007-04-10 12:58:45 +0000139# Rounding
Raymond Hettinger0ea241e2004-07-04 13:53:24 +0000140ROUND_DOWN = 'ROUND_DOWN'
141ROUND_HALF_UP = 'ROUND_HALF_UP'
142ROUND_HALF_EVEN = 'ROUND_HALF_EVEN'
143ROUND_CEILING = 'ROUND_CEILING'
144ROUND_FLOOR = 'ROUND_FLOOR'
145ROUND_UP = 'ROUND_UP'
146ROUND_HALF_DOWN = 'ROUND_HALF_DOWN'
Raymond Hettinger7c85fa42004-07-01 11:01:35 +0000147
Facundo Batista59c58842007-04-10 12:58:45 +0000148# Rounding decision (not part of the public API)
Raymond Hettinger0ea241e2004-07-04 13:53:24 +0000149NEVER_ROUND = 'NEVER_ROUND' # Round in division (non-divmod), sqrt ONLY
150ALWAYS_ROUND = 'ALWAYS_ROUND' # Every operation rounds at end.
Raymond Hettinger7c85fa42004-07-01 11:01:35 +0000151
Facundo Batista59c58842007-04-10 12:58:45 +0000152# Errors
Raymond Hettinger7c85fa42004-07-01 11:01:35 +0000153
154class DecimalException(ArithmeticError):
Raymond Hettinger5aa478b2004-07-09 10:02:53 +0000155 """Base exception class.
Raymond Hettinger7c85fa42004-07-01 11:01:35 +0000156
157 Used exceptions derive from this.
158 If an exception derives from another exception besides this (such as
159 Underflow (Inexact, Rounded, Subnormal) that indicates that it is only
160 called if the others are present. This isn't actually used for
161 anything, though.
162
Martin v. Löwiscfe31282006-07-19 17:18:32 +0000163 handle -- Called when context._raise_error is called and the
164 trap_enabler is set. First argument is self, second is the
165 context. More arguments can be given, those being after
166 the explanation in _raise_error (For example,
167 context._raise_error(NewError, '(-x)!', self._sign) would
168 call NewError().handle(context, self._sign).)
169
Raymond Hettinger7c85fa42004-07-01 11:01:35 +0000170 To define a new exception, it should be sufficient to have it derive
171 from DecimalException.
172 """
Raymond Hettinger7c85fa42004-07-01 11:01:35 +0000173 def handle(self, context, *args):
174 pass
175
176
177class Clamped(DecimalException):
178 """Exponent of a 0 changed to fit bounds.
179
180 This occurs and signals clamped if the exponent of a result has been
181 altered in order to fit the constraints of a specific concrete
Facundo Batista59c58842007-04-10 12:58:45 +0000182 representation. This may occur when the exponent of a zero result would
183 be outside the bounds of a representation, or when a large normal
184 number would have an encoded exponent that cannot be represented. In
Raymond Hettinger7c85fa42004-07-01 11:01:35 +0000185 this latter case, the exponent is reduced to fit and the corresponding
186 number of zero digits are appended to the coefficient ("fold-down").
187 """
188
189
190class InvalidOperation(DecimalException):
191 """An invalid operation was performed.
192
193 Various bad things cause this:
194
195 Something creates a signaling NaN
196 -INF + INF
Facundo Batista59c58842007-04-10 12:58:45 +0000197 0 * (+-)INF
198 (+-)INF / (+-)INF
Raymond Hettinger7c85fa42004-07-01 11:01:35 +0000199 x % 0
200 (+-)INF % x
201 x._rescale( non-integer )
202 sqrt(-x) , x > 0
203 0 ** 0
204 x ** (non-integer)
205 x ** (+-)INF
206 An operand is invalid
207 """
208 def handle(self, context, *args):
209 if args:
Facundo Batista59c58842007-04-10 12:58:45 +0000210 if args[0] == 1: # sNaN, must drop 's' but keep diagnostics
Raymond Hettinger7c85fa42004-07-01 11:01:35 +0000211 return Decimal( (args[1]._sign, args[1]._int, 'n') )
212 return NaN
213
214class ConversionSyntax(InvalidOperation):
215 """Trying to convert badly formed string.
216
217 This occurs and signals invalid-operation if an string is being
218 converted to a number and it does not conform to the numeric string
Facundo Batista59c58842007-04-10 12:58:45 +0000219 syntax. The result is [0,qNaN].
Raymond Hettinger7c85fa42004-07-01 11:01:35 +0000220 """
Facundo Batistaac4ae4b2006-07-18 12:16:13 +0000221
Martin v. Löwiscfe31282006-07-19 17:18:32 +0000222 def handle(self, context, *args):
Facundo Batista59c58842007-04-10 12:58:45 +0000223 return (0, (0,), 'n') # Passed to something which uses a tuple.
Raymond Hettinger7c85fa42004-07-01 11:01:35 +0000224
225class DivisionByZero(DecimalException, ZeroDivisionError):
226 """Division by 0.
227
228 This occurs and signals division-by-zero if division of a finite number
229 by zero was attempted (during a divide-integer or divide operation, or a
230 power operation with negative right-hand operand), and the dividend was
231 not zero.
232
233 The result of the operation is [sign,inf], where sign is the exclusive
234 or of the signs of the operands for divide, or is 1 for an odd power of
235 -0, for power.
236 """
Martin v. Löwiscfe31282006-07-19 17:18:32 +0000237
Raymond Hettinger7c85fa42004-07-01 11:01:35 +0000238 def handle(self, context, sign, double = None, *args):
239 if double is not None:
240 return (Infsign[sign],)*2
241 return Infsign[sign]
242
243class DivisionImpossible(InvalidOperation):
244 """Cannot perform the division adequately.
245
246 This occurs and signals invalid-operation if the integer result of a
247 divide-integer or remainder operation had too many digits (would be
Facundo Batista59c58842007-04-10 12:58:45 +0000248 longer than precision). The result is [0,qNaN].
Raymond Hettinger7c85fa42004-07-01 11:01:35 +0000249 """
Martin v. Löwiscfe31282006-07-19 17:18:32 +0000250
Raymond Hettinger7c85fa42004-07-01 11:01:35 +0000251 def handle(self, context, *args):
252 return (NaN, NaN)
253
254class DivisionUndefined(InvalidOperation, ZeroDivisionError):
255 """Undefined result of division.
256
257 This occurs and signals invalid-operation if division by zero was
258 attempted (during a divide-integer, divide, or remainder operation), and
Facundo Batista59c58842007-04-10 12:58:45 +0000259 the dividend is also zero. The result is [0,qNaN].
Raymond Hettinger7c85fa42004-07-01 11:01:35 +0000260 """
Martin v. Löwiscfe31282006-07-19 17:18:32 +0000261
Raymond Hettinger7c85fa42004-07-01 11:01:35 +0000262 def handle(self, context, tup=None, *args):
263 if tup is not None:
Facundo Batista59c58842007-04-10 12:58:45 +0000264 return (NaN, NaN) # for 0 %0, 0 // 0
Raymond Hettinger7c85fa42004-07-01 11:01:35 +0000265 return NaN
266
267class Inexact(DecimalException):
268 """Had to round, losing information.
269
270 This occurs and signals inexact whenever the result of an operation is
271 not exact (that is, it needed to be rounded and any discarded digits
Facundo Batista59c58842007-04-10 12:58:45 +0000272 were non-zero), or if an overflow or underflow condition occurs. The
Raymond Hettinger7c85fa42004-07-01 11:01:35 +0000273 result in all cases is unchanged.
274
275 The inexact signal may be tested (or trapped) to determine if a given
276 operation (or sequence of operations) was inexact.
277 """
Raymond Hettinger5aa478b2004-07-09 10:02:53 +0000278 pass
Raymond Hettinger7c85fa42004-07-01 11:01:35 +0000279
280class InvalidContext(InvalidOperation):
281 """Invalid context. Unknown rounding, for example.
282
283 This occurs and signals invalid-operation if an invalid context was
Facundo Batista59c58842007-04-10 12:58:45 +0000284 detected during an operation. This can occur if contexts are not checked
Raymond Hettinger7c85fa42004-07-01 11:01:35 +0000285 on creation and either the precision exceeds the capability of the
286 underlying concrete representation or an unknown or unsupported rounding
Facundo Batista59c58842007-04-10 12:58:45 +0000287 was specified. These aspects of the context need only be checked when
288 the values are required to be used. The result is [0,qNaN].
Raymond Hettinger7c85fa42004-07-01 11:01:35 +0000289 """
Martin v. Löwiscfe31282006-07-19 17:18:32 +0000290
Raymond Hettinger7c85fa42004-07-01 11:01:35 +0000291 def handle(self, context, *args):
292 return NaN
293
294class Rounded(DecimalException):
295 """Number got rounded (not necessarily changed during rounding).
296
297 This occurs and signals rounded whenever the result of an operation is
298 rounded (that is, some zero or non-zero digits were discarded from the
Facundo Batista59c58842007-04-10 12:58:45 +0000299 coefficient), or if an overflow or underflow condition occurs. The
Raymond Hettinger7c85fa42004-07-01 11:01:35 +0000300 result in all cases is unchanged.
301
302 The rounded signal may be tested (or trapped) to determine if a given
303 operation (or sequence of operations) caused a loss of precision.
304 """
Raymond Hettinger5aa478b2004-07-09 10:02:53 +0000305 pass
Raymond Hettinger7c85fa42004-07-01 11:01:35 +0000306
307class Subnormal(DecimalException):
308 """Exponent < Emin before rounding.
309
310 This occurs and signals subnormal whenever the result of a conversion or
311 operation is subnormal (that is, its adjusted exponent is less than
Facundo Batista59c58842007-04-10 12:58:45 +0000312 Emin, before any rounding). The result in all cases is unchanged.
Raymond Hettinger7c85fa42004-07-01 11:01:35 +0000313
314 The subnormal signal may be tested (or trapped) to determine if a given
315 or operation (or sequence of operations) yielded a subnormal result.
316 """
317 pass
318
319class Overflow(Inexact, Rounded):
320 """Numerical overflow.
321
322 This occurs and signals overflow if the adjusted exponent of a result
323 (from a conversion or from an operation that is not an attempt to divide
324 by zero), after rounding, would be greater than the largest value that
325 can be handled by the implementation (the value Emax).
326
327 The result depends on the rounding mode:
328
329 For round-half-up and round-half-even (and for round-half-down and
330 round-up, if implemented), the result of the operation is [sign,inf],
Facundo Batista59c58842007-04-10 12:58:45 +0000331 where sign is the sign of the intermediate result. For round-down, the
Raymond Hettinger7c85fa42004-07-01 11:01:35 +0000332 result is the largest finite number that can be represented in the
Facundo Batista59c58842007-04-10 12:58:45 +0000333 current precision, with the sign of the intermediate result. For
Raymond Hettinger7c85fa42004-07-01 11:01:35 +0000334 round-ceiling, the result is the same as for round-down if the sign of
Facundo Batista59c58842007-04-10 12:58:45 +0000335 the intermediate result is 1, or is [0,inf] otherwise. For round-floor,
Raymond Hettinger7c85fa42004-07-01 11:01:35 +0000336 the result is the same as for round-down if the sign of the intermediate
Facundo Batista59c58842007-04-10 12:58:45 +0000337 result is 0, or is [1,inf] otherwise. In all cases, Inexact and Rounded
Raymond Hettinger7c85fa42004-07-01 11:01:35 +0000338 will also be raised.
Martin v. Löwiscfe31282006-07-19 17:18:32 +0000339 """
340
Raymond Hettinger7c85fa42004-07-01 11:01:35 +0000341 def handle(self, context, sign, *args):
342 if context.rounding in (ROUND_HALF_UP, ROUND_HALF_EVEN,
343 ROUND_HALF_DOWN, ROUND_UP):
344 return Infsign[sign]
345 if sign == 0:
346 if context.rounding == ROUND_CEILING:
347 return Infsign[sign]
348 return Decimal((sign, (9,)*context.prec,
349 context.Emax-context.prec+1))
350 if sign == 1:
351 if context.rounding == ROUND_FLOOR:
352 return Infsign[sign]
353 return Decimal( (sign, (9,)*context.prec,
354 context.Emax-context.prec+1))
355
356
357class Underflow(Inexact, Rounded, Subnormal):
358 """Numerical underflow with result rounded to 0.
359
360 This occurs and signals underflow if a result is inexact and the
361 adjusted exponent of the result would be smaller (more negative) than
362 the smallest value that can be handled by the implementation (the value
Facundo Batista59c58842007-04-10 12:58:45 +0000363 Emin). That is, the result is both inexact and subnormal.
Raymond Hettinger7c85fa42004-07-01 11:01:35 +0000364
365 The result after an underflow will be a subnormal number rounded, if
Facundo Batista59c58842007-04-10 12:58:45 +0000366 necessary, so that its exponent is not less than Etiny. This may result
Raymond Hettinger7c85fa42004-07-01 11:01:35 +0000367 in 0 with the sign of the intermediate result and an exponent of Etiny.
368
369 In all cases, Inexact, Rounded, and Subnormal will also be raised.
370 """
371
Raymond Hettinger5aa478b2004-07-09 10:02:53 +0000372# List of public traps and flags
Raymond Hettingerfed52962004-07-14 15:41:57 +0000373_signals = [Clamped, DivisionByZero, Inexact, Overflow, Rounded,
Martin v. Löwiscfe31282006-07-19 17:18:32 +0000374 Underflow, InvalidOperation, Subnormal]
Raymond Hettinger7c85fa42004-07-01 11:01:35 +0000375
Raymond Hettinger5aa478b2004-07-09 10:02:53 +0000376# Map conditions (per the spec) to signals
377_condition_map = {ConversionSyntax:InvalidOperation,
378 DivisionImpossible:InvalidOperation,
379 DivisionUndefined:InvalidOperation,
380 InvalidContext:InvalidOperation}
Raymond Hettinger7c85fa42004-07-01 11:01:35 +0000381
Facundo Batista59c58842007-04-10 12:58:45 +0000382##### Context Functions ##################################################
Raymond Hettinger7c85fa42004-07-01 11:01:35 +0000383
Raymond Hettingeref66deb2004-07-14 21:04:27 +0000384# The getcontext() and setcontext() function manage access to a thread-local
385# current context. Py2.4 offers direct support for thread locals. If that
386# is not available, use threading.currentThread() which is slower but will
Raymond Hettinger7e71fa52004-12-18 19:07:19 +0000387# work for older Pythons. If threads are not part of the build, create a
Martin v. Löwiscfe31282006-07-19 17:18:32 +0000388# mock threading object with threading.local() returning the module namespace.
Raymond Hettinger7e71fa52004-12-18 19:07:19 +0000389
390try:
391 import threading
392except ImportError:
393 # Python was compiled without threads; create a mock object instead
394 import sys
Facundo Batista59c58842007-04-10 12:58:45 +0000395 class MockThreading(object):
Raymond Hettinger7e71fa52004-12-18 19:07:19 +0000396 def local(self, sys=sys):
397 return sys.modules[__name__]
398 threading = MockThreading()
399 del sys, MockThreading
Raymond Hettinger7c85fa42004-07-01 11:01:35 +0000400
Raymond Hettingeref66deb2004-07-14 21:04:27 +0000401try:
402 threading.local
Raymond Hettinger7c85fa42004-07-01 11:01:35 +0000403
Raymond Hettingeref66deb2004-07-14 21:04:27 +0000404except AttributeError:
Raymond Hettinger7c85fa42004-07-01 11:01:35 +0000405
Facundo Batista59c58842007-04-10 12:58:45 +0000406 # To fix reloading, force it to create a new context
407 # Old contexts have different exceptions in their dicts, making problems.
Raymond Hettingeref66deb2004-07-14 21:04:27 +0000408 if hasattr(threading.currentThread(), '__decimal_context__'):
409 del threading.currentThread().__decimal_context__
410
411 def setcontext(context):
412 """Set this thread's context to context."""
413 if context in (DefaultContext, BasicContext, ExtendedContext):
Raymond Hettinger9fce44b2004-08-08 04:03:24 +0000414 context = context.copy()
Raymond Hettinger61992ef2004-08-06 23:42:16 +0000415 context.clear_flags()
Raymond Hettinger7c85fa42004-07-01 11:01:35 +0000416 threading.currentThread().__decimal_context__ = context
Raymond Hettingeref66deb2004-07-14 21:04:27 +0000417
418 def getcontext():
419 """Returns this thread's context.
420
421 If this thread does not yet have a context, returns
422 a new context and sets this thread's context.
423 New contexts are copies of DefaultContext.
424 """
425 try:
426 return threading.currentThread().__decimal_context__
427 except AttributeError:
428 context = Context()
429 threading.currentThread().__decimal_context__ = context
430 return context
431
432else:
433
434 local = threading.local()
Raymond Hettinger9fce44b2004-08-08 04:03:24 +0000435 if hasattr(local, '__decimal_context__'):
436 del local.__decimal_context__
Raymond Hettingeref66deb2004-07-14 21:04:27 +0000437
438 def getcontext(_local=local):
439 """Returns this thread's context.
440
441 If this thread does not yet have a context, returns
442 a new context and sets this thread's context.
443 New contexts are copies of DefaultContext.
444 """
445 try:
446 return _local.__decimal_context__
447 except AttributeError:
448 context = Context()
449 _local.__decimal_context__ = context
450 return context
451
452 def setcontext(context, _local=local):
453 """Set this thread's context to context."""
454 if context in (DefaultContext, BasicContext, ExtendedContext):
Raymond Hettinger9fce44b2004-08-08 04:03:24 +0000455 context = context.copy()
Raymond Hettinger61992ef2004-08-06 23:42:16 +0000456 context.clear_flags()
Raymond Hettingeref66deb2004-07-14 21:04:27 +0000457 _local.__decimal_context__ = context
458
Martin v. Löwiscfe31282006-07-19 17:18:32 +0000459 del threading, local # Don't contaminate the namespace
Raymond Hettinger7c85fa42004-07-01 11:01:35 +0000460
Nick Coghlan8b6999b2006-08-31 12:00:43 +0000461def localcontext(ctx=None):
462 """Return a context manager for a copy of the supplied context
463
464 Uses a copy of the current context if no context is specified
465 The returned context manager creates a local decimal context
466 in a with statement:
467 def sin(x):
468 with localcontext() as ctx:
469 ctx.prec += 2
470 # Rest of sin calculation algorithm
471 # uses a precision 2 greater than normal
Facundo Batista59c58842007-04-10 12:58:45 +0000472 return +s # Convert result to normal precision
Nick Coghlan8b6999b2006-08-31 12:00:43 +0000473
474 def sin(x):
475 with localcontext(ExtendedContext):
476 # Rest of sin calculation algorithm
477 # uses the Extended Context from the
478 # General Decimal Arithmetic Specification
Facundo Batista59c58842007-04-10 12:58:45 +0000479 return +s # Convert result to normal context
Nick Coghlan8b6999b2006-08-31 12:00:43 +0000480
481 """
Neal Norwitz681d8672006-09-02 18:51:34 +0000482 # The string below can't be included in the docstring until Python 2.6
Nick Coghlan8b6999b2006-08-31 12:00:43 +0000483 # as the doctest module doesn't understand __future__ statements
484 """
485 >>> from __future__ import with_statement
486 >>> print getcontext().prec
487 28
488 >>> with localcontext():
489 ... ctx = getcontext()
Raymond Hettinger495df472007-02-08 01:42:35 +0000490 ... ctx.prec += 2
Nick Coghlan8b6999b2006-08-31 12:00:43 +0000491 ... print ctx.prec
492 ...
493 30
494 >>> with localcontext(ExtendedContext):
495 ... print getcontext().prec
496 ...
497 9
498 >>> print getcontext().prec
499 28
500 """
Nick Coghlanced12182006-09-02 03:54:17 +0000501 if ctx is None: ctx = getcontext()
502 return _ContextManager(ctx)
Nick Coghlan8b6999b2006-08-31 12:00:43 +0000503
Raymond Hettinger7c85fa42004-07-01 11:01:35 +0000504
Facundo Batista59c58842007-04-10 12:58:45 +0000505##### Decimal class #######################################################
Raymond Hettinger7c85fa42004-07-01 11:01:35 +0000506
507class Decimal(object):
508 """Floating point class for decimal arithmetic."""
509
Raymond Hettinger636a6b12004-09-19 01:54:09 +0000510 __slots__ = ('_exp','_int','_sign', '_is_special')
511 # Generally, the value of the Decimal instance is given by
512 # (-1)**_sign * _int * 10**_exp
513 # Special values are signified by _is_special == True
Raymond Hettinger7c85fa42004-07-01 11:01:35 +0000514
Raymond Hettingerdab988d2004-10-09 07:10:44 +0000515 # We're immutable, so use __new__ not __init__
Raymond Hettinger636a6b12004-09-19 01:54:09 +0000516 def __new__(cls, value="0", context=None):
Raymond Hettinger7c85fa42004-07-01 11:01:35 +0000517 """Create a decimal point instance.
518
519 >>> Decimal('3.14') # string input
520 Decimal("3.14")
Facundo Batista59c58842007-04-10 12:58:45 +0000521 >>> Decimal((0, (3, 1, 4), -2)) # tuple (sign, digit_tuple, exponent)
Raymond Hettinger7c85fa42004-07-01 11:01:35 +0000522 Decimal("3.14")
523 >>> Decimal(314) # int or long
524 Decimal("314")
525 >>> Decimal(Decimal(314)) # another decimal instance
526 Decimal("314")
527 """
Raymond Hettinger7c85fa42004-07-01 11:01:35 +0000528
Raymond Hettinger636a6b12004-09-19 01:54:09 +0000529 self = object.__new__(cls)
530 self._is_special = False
531
532 # From an internal working value
533 if isinstance(value, _WorkRep):
Raymond Hettinger17931de2004-10-27 06:21:46 +0000534 self._sign = value.sign
Raymond Hettinger636a6b12004-09-19 01:54:09 +0000535 self._int = tuple(map(int, str(value.int)))
536 self._exp = int(value.exp)
537 return self
538
539 # From another decimal
540 if isinstance(value, Decimal):
541 self._exp = value._exp
542 self._sign = value._sign
543 self._int = value._int
544 self._is_special = value._is_special
545 return self
546
547 # From an integer
Raymond Hettinger7c85fa42004-07-01 11:01:35 +0000548 if isinstance(value, (int,long)):
Raymond Hettinger636a6b12004-09-19 01:54:09 +0000549 if value >= 0:
550 self._sign = 0
551 else:
552 self._sign = 1
553 self._exp = 0
554 self._int = tuple(map(int, str(abs(value))))
555 return self
Raymond Hettinger7c85fa42004-07-01 11:01:35 +0000556
557 # tuple/list conversion (possibly from as_tuple())
558 if isinstance(value, (list,tuple)):
559 if len(value) != 3:
Facundo Batista59c58842007-04-10 12:58:45 +0000560 raise ValueError('Invalid arguments')
Raymond Hettingerdbecd932005-02-06 06:57:08 +0000561 if value[0] not in (0,1):
Facundo Batista59c58842007-04-10 12:58:45 +0000562 raise ValueError('Invalid sign')
Raymond Hettinger7c85fa42004-07-01 11:01:35 +0000563 for digit in value[1]:
564 if not isinstance(digit, (int,long)) or digit < 0:
Facundo Batista59c58842007-04-10 12:58:45 +0000565 raise ValueError("The second value in the tuple must be"
566 "composed of non negative integer elements.")
Raymond Hettinger7c85fa42004-07-01 11:01:35 +0000567 self._sign = value[0]
568 self._int = tuple(value[1])
569 if value[2] in ('F','n','N'):
570 self._exp = value[2]
Raymond Hettinger636a6b12004-09-19 01:54:09 +0000571 self._is_special = True
Raymond Hettinger7c85fa42004-07-01 11:01:35 +0000572 else:
573 self._exp = int(value[2])
Raymond Hettinger636a6b12004-09-19 01:54:09 +0000574 return self
Raymond Hettinger7c85fa42004-07-01 11:01:35 +0000575
Raymond Hettingerbf440692004-07-10 14:14:37 +0000576 if isinstance(value, float):
577 raise TypeError("Cannot convert float to Decimal. " +
578 "First convert the float to a string")
579
Raymond Hettinger636a6b12004-09-19 01:54:09 +0000580 # Other argument types may require the context during interpretation
581 if context is None:
582 context = getcontext()
Raymond Hettinger7c85fa42004-07-01 11:01:35 +0000583
Raymond Hettinger636a6b12004-09-19 01:54:09 +0000584 # From a string
585 # REs insist on real strings, so we can too.
586 if isinstance(value, basestring):
587 if _isinfinity(value):
588 self._exp = 'F'
589 self._int = (0,)
590 self._is_special = True
591 if _isinfinity(value) == 1:
592 self._sign = 0
593 else:
594 self._sign = 1
595 return self
596 if _isnan(value):
597 sig, sign, diag = _isnan(value)
598 self._is_special = True
Facundo Batista59c58842007-04-10 12:58:45 +0000599 if len(diag) > context.prec: # Diagnostic info too long
Raymond Hettinger636a6b12004-09-19 01:54:09 +0000600 self._sign, self._int, self._exp = \
601 context._raise_error(ConversionSyntax)
602 return self
603 if sig == 1:
Facundo Batista59c58842007-04-10 12:58:45 +0000604 self._exp = 'n' # qNaN
605 else: # sig == 2
606 self._exp = 'N' # sNaN
Raymond Hettinger636a6b12004-09-19 01:54:09 +0000607 self._sign = sign
Facundo Batista59c58842007-04-10 12:58:45 +0000608 self._int = tuple(map(int, diag)) # Diagnostic info
Raymond Hettinger636a6b12004-09-19 01:54:09 +0000609 return self
610 try:
611 self._sign, self._int, self._exp = _string2exact(value)
612 except ValueError:
613 self._is_special = True
Facundo Batista59c58842007-04-10 12:58:45 +0000614 self._sign, self._int, self._exp = \
615 context._raise_error(ConversionSyntax)
Raymond Hettinger636a6b12004-09-19 01:54:09 +0000616 return self
Raymond Hettinger7c85fa42004-07-01 11:01:35 +0000617
Raymond Hettinger636a6b12004-09-19 01:54:09 +0000618 raise TypeError("Cannot convert %r to Decimal" % value)
Raymond Hettinger7c85fa42004-07-01 11:01:35 +0000619
620 def _isnan(self):
621 """Returns whether the number is not actually one.
622
623 0 if a number
624 1 if NaN
625 2 if sNaN
626 """
Raymond Hettinger636a6b12004-09-19 01:54:09 +0000627 if self._is_special:
628 exp = self._exp
629 if exp == 'n':
630 return 1
631 elif exp == 'N':
632 return 2
Raymond Hettinger7c85fa42004-07-01 11:01:35 +0000633 return 0
634
635 def _isinfinity(self):
636 """Returns whether the number is infinite
637
638 0 if finite or not a number
639 1 if +INF
640 -1 if -INF
641 """
642 if self._exp == 'F':
643 if self._sign:
644 return -1
645 return 1
646 return 0
647
648 def _check_nans(self, other = None, context=None):
649 """Returns whether the number is not actually one.
650
651 if self, other are sNaN, signal
652 if self, other are NaN return nan
653 return 0
654
655 Done before operations.
656 """
Raymond Hettinger7c85fa42004-07-01 11:01:35 +0000657
Raymond Hettinger636a6b12004-09-19 01:54:09 +0000658 self_is_nan = self._isnan()
659 if other is None:
660 other_is_nan = False
661 else:
662 other_is_nan = other._isnan()
663
664 if self_is_nan or other_is_nan:
665 if context is None:
666 context = getcontext()
667
668 if self_is_nan == 2:
669 return context._raise_error(InvalidOperation, 'sNaN',
670 1, self)
671 if other_is_nan == 2:
672 return context._raise_error(InvalidOperation, 'sNaN',
673 1, other)
674 if self_is_nan:
675 return self
676
Raymond Hettinger7c85fa42004-07-01 11:01:35 +0000677 return other
678 return 0
679
Raymond Hettinger7c85fa42004-07-01 11:01:35 +0000680 def __nonzero__(self):
681 """Is the number non-zero?
682
683 0 if self == 0
684 1 if self != 0
685 """
Raymond Hettinger636a6b12004-09-19 01:54:09 +0000686 if self._is_special:
Raymond Hettinger7c85fa42004-07-01 11:01:35 +0000687 return 1
Raymond Hettinger636a6b12004-09-19 01:54:09 +0000688 return sum(self._int) != 0
Raymond Hettinger7c85fa42004-07-01 11:01:35 +0000689
690 def __cmp__(self, other, context=None):
Raymond Hettinger636a6b12004-09-19 01:54:09 +0000691 other = _convert_other(other)
Raymond Hettinger267b8682005-03-27 10:47:39 +0000692 if other is NotImplemented:
693 return other
Raymond Hettinger7c85fa42004-07-01 11:01:35 +0000694
Raymond Hettinger636a6b12004-09-19 01:54:09 +0000695 if self._is_special or other._is_special:
696 ans = self._check_nans(other, context)
697 if ans:
Facundo Batista59c58842007-04-10 12:58:45 +0000698 return 1 # Comparison involving NaN's always reports self > other
Raymond Hettinger636a6b12004-09-19 01:54:09 +0000699
700 # INF = INF
701 return cmp(self._isinfinity(), other._isinfinity())
Raymond Hettinger7c85fa42004-07-01 11:01:35 +0000702
703 if not self and not other:
Facundo Batista59c58842007-04-10 12:58:45 +0000704 return 0 # If both 0, sign comparison isn't certain.
Raymond Hettinger7c85fa42004-07-01 11:01:35 +0000705
Facundo Batista59c58842007-04-10 12:58:45 +0000706 # If different signs, neg one is less
Raymond Hettinger7c85fa42004-07-01 11:01:35 +0000707 if other._sign < self._sign:
708 return -1
709 if self._sign < other._sign:
710 return 1
711
Raymond Hettinger636a6b12004-09-19 01:54:09 +0000712 self_adjusted = self.adjusted()
713 other_adjusted = other.adjusted()
714 if self_adjusted == other_adjusted and \
Raymond Hettinger7c85fa42004-07-01 11:01:35 +0000715 self._int + (0,)*(self._exp - other._exp) == \
716 other._int + (0,)*(other._exp - self._exp):
Facundo Batista59c58842007-04-10 12:58:45 +0000717 return 0 # equal, except in precision. ([0]*(-x) = [])
Raymond Hettinger636a6b12004-09-19 01:54:09 +0000718 elif self_adjusted > other_adjusted and self._int[0] != 0:
Raymond Hettinger7c85fa42004-07-01 11:01:35 +0000719 return (-1)**self._sign
Raymond Hettinger636a6b12004-09-19 01:54:09 +0000720 elif self_adjusted < other_adjusted and other._int[0] != 0:
Raymond Hettinger7c85fa42004-07-01 11:01:35 +0000721 return -((-1)**self._sign)
722
Raymond Hettinger636a6b12004-09-19 01:54:09 +0000723 # Need to round, so make sure we have a valid context
724 if context is None:
725 context = getcontext()
726
Raymond Hettinger9fce44b2004-08-08 04:03:24 +0000727 context = context._shallow_copy()
Facundo Batista59c58842007-04-10 12:58:45 +0000728 rounding = context._set_rounding(ROUND_UP) # round away from 0
Raymond Hettinger7c85fa42004-07-01 11:01:35 +0000729
730 flags = context._ignore_all_flags()
731 res = self.__sub__(other, context=context)
732
733 context._regard_flags(*flags)
734
735 context.rounding = rounding
736
737 if not res:
738 return 0
739 elif res._sign:
740 return -1
741 return 1
742
Raymond Hettinger0aeac102004-07-05 22:53:03 +0000743 def __eq__(self, other):
744 if not isinstance(other, (Decimal, int, long)):
Raymond Hettinger267b8682005-03-27 10:47:39 +0000745 return NotImplemented
Raymond Hettinger0aeac102004-07-05 22:53:03 +0000746 return self.__cmp__(other) == 0
747
748 def __ne__(self, other):
749 if not isinstance(other, (Decimal, int, long)):
Raymond Hettinger267b8682005-03-27 10:47:39 +0000750 return NotImplemented
Raymond Hettinger0aeac102004-07-05 22:53:03 +0000751 return self.__cmp__(other) != 0
752
Raymond Hettinger7c85fa42004-07-01 11:01:35 +0000753 def compare(self, other, context=None):
754 """Compares one to another.
755
756 -1 => a < b
757 0 => a = b
758 1 => a > b
759 NaN => one is NaN
760 Like __cmp__, but returns Decimal instances.
761 """
Raymond Hettinger636a6b12004-09-19 01:54:09 +0000762 other = _convert_other(other)
Raymond Hettinger267b8682005-03-27 10:47:39 +0000763 if other is NotImplemented:
764 return other
Raymond Hettinger7c85fa42004-07-01 11:01:35 +0000765
Facundo Batista59c58842007-04-10 12:58:45 +0000766 # Compare(NaN, NaN) = NaN
Raymond Hettinger636a6b12004-09-19 01:54:09 +0000767 if (self._is_special or other and other._is_special):
768 ans = self._check_nans(other, context)
769 if ans:
770 return ans
Raymond Hettinger7c85fa42004-07-01 11:01:35 +0000771
772 return Decimal(self.__cmp__(other, context))
773
774 def __hash__(self):
775 """x.__hash__() <==> hash(x)"""
776 # Decimal integers must hash the same as the ints
777 # Non-integer decimals are normalized and hashed as strings
Georg Brandl1fb9f522006-05-11 19:57:09 +0000778 # Normalization assures that hash(100E-1) == hash(10)
Raymond Hettingerbea3f6f2005-03-15 04:59:17 +0000779 if self._is_special:
780 if self._isnan():
781 raise TypeError('Cannot hash a NaN value.')
782 return hash(str(self))
Raymond Hettinger7c85fa42004-07-01 11:01:35 +0000783 i = int(self)
784 if self == Decimal(i):
785 return hash(i)
786 assert self.__nonzero__() # '-0' handled by integer case
787 return hash(str(self.normalize()))
788
789 def as_tuple(self):
790 """Represents the number as a triple tuple.
791
792 To show the internals exactly as they are.
793 """
794 return (self._sign, self._int, self._exp)
795
796 def __repr__(self):
797 """Represents the number as an instance of Decimal."""
798 # Invariant: eval(repr(d)) == d
799 return 'Decimal("%s")' % str(self)
800
801 def __str__(self, eng = 0, context=None):
802 """Return string representation of the number in scientific notation.
803
804 Captures all of the information in the underlying representation.
805 """
806
Raymond Hettingere5a0a962005-06-20 09:49:42 +0000807 if self._is_special:
808 if self._isnan():
809 minus = '-'*self._sign
810 if self._int == (0,):
811 info = ''
812 else:
813 info = ''.join(map(str, self._int))
814 if self._isnan() == 2:
815 return minus + 'sNaN' + info
816 return minus + 'NaN' + info
817 if self._isinfinity():
818 minus = '-'*self._sign
819 return minus + 'Infinity'
Raymond Hettinger7c85fa42004-07-01 11:01:35 +0000820
821 if context is None:
822 context = getcontext()
823
824 tmp = map(str, self._int)
825 numdigits = len(self._int)
826 leftdigits = self._exp + numdigits
Facundo Batista59c58842007-04-10 12:58:45 +0000827 if eng and not self: # self = 0eX wants 0[.0[0]]eY, not [[0]0]0eY
828 if self._exp < 0 and self._exp >= -6: # short, no need for e/E
Raymond Hettinger7c85fa42004-07-01 11:01:35 +0000829 s = '-'*self._sign + '0.' + '0'*(abs(self._exp))
830 return s
Facundo Batista59c58842007-04-10 12:58:45 +0000831 # exp is closest mult. of 3 >= self._exp
Raymond Hettinger7c85fa42004-07-01 11:01:35 +0000832 exp = ((self._exp - 1)// 3 + 1) * 3
833 if exp != self._exp:
834 s = '0.'+'0'*(exp - self._exp)
835 else:
836 s = '0'
837 if exp != 0:
838 if context.capitals:
839 s += 'E'
840 else:
841 s += 'e'
842 if exp > 0:
Facundo Batista59c58842007-04-10 12:58:45 +0000843 s += '+' # 0.0e+3, not 0.0e3
Raymond Hettinger7c85fa42004-07-01 11:01:35 +0000844 s += str(exp)
845 s = '-'*self._sign + s
846 return s
847 if eng:
848 dotplace = (leftdigits-1)%3+1
849 adjexp = leftdigits -1 - (leftdigits-1)%3
850 else:
851 adjexp = leftdigits-1
852 dotplace = 1
853 if self._exp == 0:
854 pass
855 elif self._exp < 0 and adjexp >= 0:
856 tmp.insert(leftdigits, '.')
857 elif self._exp < 0 and adjexp >= -6:
858 tmp[0:0] = ['0'] * int(-leftdigits)
859 tmp.insert(0, '0.')
860 else:
861 if numdigits > dotplace:
862 tmp.insert(dotplace, '.')
863 elif numdigits < dotplace:
864 tmp.extend(['0']*(dotplace-numdigits))
865 if adjexp:
866 if not context.capitals:
867 tmp.append('e')
868 else:
869 tmp.append('E')
870 if adjexp > 0:
871 tmp.append('+')
872 tmp.append(str(adjexp))
873 if eng:
874 while tmp[0:1] == ['0']:
875 tmp[0:1] = []
876 if len(tmp) == 0 or tmp[0] == '.' or tmp[0].lower() == 'e':
877 tmp[0:0] = ['0']
878 if self._sign:
879 tmp.insert(0, '-')
880
881 return ''.join(tmp)
882
883 def to_eng_string(self, context=None):
884 """Convert to engineering-type string.
885
886 Engineering notation has an exponent which is a multiple of 3, so there
887 are up to 3 digits left of the decimal place.
888
889 Same rules for when in exponential and when as a value as in __str__.
890 """
Raymond Hettinger7c85fa42004-07-01 11:01:35 +0000891 return self.__str__(eng=1, context=context)
892
893 def __neg__(self, context=None):
894 """Returns a copy with the sign switched.
895
896 Rounds, if it has reason.
897 """
Raymond Hettinger636a6b12004-09-19 01:54:09 +0000898 if self._is_special:
899 ans = self._check_nans(context=context)
900 if ans:
901 return ans
Raymond Hettinger7c85fa42004-07-01 11:01:35 +0000902
903 if not self:
904 # -Decimal('0') is Decimal('0'), not Decimal('-0')
905 sign = 0
906 elif self._sign:
907 sign = 0
908 else:
909 sign = 1
Raymond Hettinger636a6b12004-09-19 01:54:09 +0000910
911 if context is None:
912 context = getcontext()
Raymond Hettinger7c85fa42004-07-01 11:01:35 +0000913 if context._rounding_decision == ALWAYS_ROUND:
Raymond Hettingerdab988d2004-10-09 07:10:44 +0000914 return Decimal((sign, self._int, self._exp))._fix(context)
Raymond Hettinger7c85fa42004-07-01 11:01:35 +0000915 return Decimal( (sign, self._int, self._exp))
916
917 def __pos__(self, context=None):
918 """Returns a copy, unless it is a sNaN.
919
920 Rounds the number (if more then precision digits)
921 """
Raymond Hettinger636a6b12004-09-19 01:54:09 +0000922 if self._is_special:
923 ans = self._check_nans(context=context)
924 if ans:
925 return ans
Raymond Hettinger7c85fa42004-07-01 11:01:35 +0000926
927 sign = self._sign
928 if not self:
929 # + (-0) = 0
930 sign = 0
931
Raymond Hettinger636a6b12004-09-19 01:54:09 +0000932 if context is None:
933 context = getcontext()
934
Raymond Hettinger7c85fa42004-07-01 11:01:35 +0000935 if context._rounding_decision == ALWAYS_ROUND:
Raymond Hettingerdab988d2004-10-09 07:10:44 +0000936 ans = self._fix(context)
Raymond Hettinger7c85fa42004-07-01 11:01:35 +0000937 else:
938 ans = Decimal(self)
939 ans._sign = sign
940 return ans
941
942 def __abs__(self, round=1, context=None):
943 """Returns the absolute value of self.
944
945 If the second argument is 0, do not round.
946 """
Raymond Hettinger636a6b12004-09-19 01:54:09 +0000947 if self._is_special:
948 ans = self._check_nans(context=context)
949 if ans:
950 return ans
Raymond Hettinger7c85fa42004-07-01 11:01:35 +0000951
952 if not round:
Raymond Hettinger636a6b12004-09-19 01:54:09 +0000953 if context is None:
954 context = getcontext()
Raymond Hettinger9fce44b2004-08-08 04:03:24 +0000955 context = context._shallow_copy()
Raymond Hettinger7c85fa42004-07-01 11:01:35 +0000956 context._set_rounding_decision(NEVER_ROUND)
957
958 if self._sign:
959 ans = self.__neg__(context=context)
960 else:
961 ans = self.__pos__(context=context)
962
963 return ans
964
965 def __add__(self, other, context=None):
966 """Returns self + other.
967
968 -INF + INF (or the reverse) cause InvalidOperation errors.
969 """
Raymond Hettinger636a6b12004-09-19 01:54:09 +0000970 other = _convert_other(other)
Raymond Hettinger267b8682005-03-27 10:47:39 +0000971 if other is NotImplemented:
972 return other
Raymond Hettinger636a6b12004-09-19 01:54:09 +0000973
Raymond Hettinger7c85fa42004-07-01 11:01:35 +0000974 if context is None:
975 context = getcontext()
Raymond Hettinger7c85fa42004-07-01 11:01:35 +0000976
Raymond Hettinger636a6b12004-09-19 01:54:09 +0000977 if self._is_special or other._is_special:
978 ans = self._check_nans(other, context)
979 if ans:
980 return ans
Raymond Hettinger7c85fa42004-07-01 11:01:35 +0000981
Raymond Hettinger636a6b12004-09-19 01:54:09 +0000982 if self._isinfinity():
Facundo Batista59c58842007-04-10 12:58:45 +0000983 # If both INF, same sign => same as both, opposite => error.
Raymond Hettinger636a6b12004-09-19 01:54:09 +0000984 if self._sign != other._sign and other._isinfinity():
985 return context._raise_error(InvalidOperation, '-INF + INF')
986 return Decimal(self)
987 if other._isinfinity():
Facundo Batista59c58842007-04-10 12:58:45 +0000988 return Decimal(other) # Can't both be infinity here
Raymond Hettinger7c85fa42004-07-01 11:01:35 +0000989
990 shouldround = context._rounding_decision == ALWAYS_ROUND
991
992 exp = min(self._exp, other._exp)
993 negativezero = 0
994 if context.rounding == ROUND_FLOOR and self._sign != other._sign:
Facundo Batista59c58842007-04-10 12:58:45 +0000995 # If the answer is 0, the sign should be negative, in this case.
Raymond Hettinger7c85fa42004-07-01 11:01:35 +0000996 negativezero = 1
997
998 if not self and not other:
999 sign = min(self._sign, other._sign)
1000 if negativezero:
1001 sign = 1
1002 return Decimal( (sign, (0,), exp))
1003 if not self:
Facundo Batista99b55482004-10-26 23:38:46 +00001004 exp = max(exp, other._exp - context.prec-1)
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00001005 ans = other._rescale(exp, watchexp=0, context=context)
1006 if shouldround:
Raymond Hettingerdab988d2004-10-09 07:10:44 +00001007 ans = ans._fix(context)
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00001008 return ans
1009 if not other:
Facundo Batista99b55482004-10-26 23:38:46 +00001010 exp = max(exp, self._exp - context.prec-1)
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00001011 ans = self._rescale(exp, watchexp=0, context=context)
1012 if shouldround:
Raymond Hettingerdab988d2004-10-09 07:10:44 +00001013 ans = ans._fix(context)
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00001014 return ans
1015
1016 op1 = _WorkRep(self)
1017 op2 = _WorkRep(other)
1018 op1, op2 = _normalize(op1, op2, shouldround, context.prec)
1019
1020 result = _WorkRep()
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00001021 if op1.sign != op2.sign:
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00001022 # Equal and opposite
Raymond Hettinger17931de2004-10-27 06:21:46 +00001023 if op1.int == op2.int:
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00001024 if exp < context.Etiny():
1025 exp = context.Etiny()
1026 context._raise_error(Clamped)
1027 return Decimal((negativezero, (0,), exp))
Raymond Hettinger17931de2004-10-27 06:21:46 +00001028 if op1.int < op2.int:
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00001029 op1, op2 = op2, op1
Facundo Batista59c58842007-04-10 12:58:45 +00001030 # OK, now abs(op1) > abs(op2)
Raymond Hettinger17931de2004-10-27 06:21:46 +00001031 if op1.sign == 1:
1032 result.sign = 1
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00001033 op1.sign, op2.sign = op2.sign, op1.sign
1034 else:
Raymond Hettinger17931de2004-10-27 06:21:46 +00001035 result.sign = 0
Facundo Batista59c58842007-04-10 12:58:45 +00001036 # So we know the sign, and op1 > 0.
Raymond Hettinger17931de2004-10-27 06:21:46 +00001037 elif op1.sign == 1:
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00001038 result.sign = 1
Raymond Hettinger17931de2004-10-27 06:21:46 +00001039 op1.sign, op2.sign = (0, 0)
1040 else:
1041 result.sign = 0
Facundo Batista59c58842007-04-10 12:58:45 +00001042 # Now, op1 > abs(op2) > 0
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00001043
Raymond Hettinger17931de2004-10-27 06:21:46 +00001044 if op2.sign == 0:
Raymond Hettinger636a6b12004-09-19 01:54:09 +00001045 result.int = op1.int + op2.int
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00001046 else:
Raymond Hettinger636a6b12004-09-19 01:54:09 +00001047 result.int = op1.int - op2.int
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00001048
1049 result.exp = op1.exp
1050 ans = Decimal(result)
1051 if shouldround:
Raymond Hettingerdab988d2004-10-09 07:10:44 +00001052 ans = ans._fix(context)
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00001053 return ans
1054
1055 __radd__ = __add__
1056
1057 def __sub__(self, other, context=None):
1058 """Return self + (-other)"""
Raymond Hettinger636a6b12004-09-19 01:54:09 +00001059 other = _convert_other(other)
Raymond Hettinger267b8682005-03-27 10:47:39 +00001060 if other is NotImplemented:
1061 return other
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00001062
Raymond Hettinger636a6b12004-09-19 01:54:09 +00001063 if self._is_special or other._is_special:
1064 ans = self._check_nans(other, context=context)
1065 if ans:
1066 return ans
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00001067
1068 # -Decimal(0) = Decimal(0), which we don't want since
1069 # (-0 - 0 = -0 + (-0) = -0, but -0 + 0 = 0.)
1070 # so we change the sign directly to a copy
1071 tmp = Decimal(other)
1072 tmp._sign = 1-tmp._sign
1073
1074 return self.__add__(tmp, context=context)
1075
1076 def __rsub__(self, other, context=None):
1077 """Return other + (-self)"""
Raymond Hettinger636a6b12004-09-19 01:54:09 +00001078 other = _convert_other(other)
Raymond Hettinger267b8682005-03-27 10:47:39 +00001079 if other is NotImplemented:
1080 return other
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00001081
1082 tmp = Decimal(self)
1083 tmp._sign = 1 - tmp._sign
1084 return other.__add__(tmp, context=context)
1085
1086 def _increment(self, round=1, context=None):
1087 """Special case of add, adding 1eExponent
1088
1089 Since it is common, (rounding, for example) this adds
1090 (sign)*one E self._exp to the number more efficiently than add.
1091
1092 For example:
1093 Decimal('5.624e10')._increment() == Decimal('5.625e10')
1094 """
Raymond Hettinger636a6b12004-09-19 01:54:09 +00001095 if self._is_special:
1096 ans = self._check_nans(context=context)
1097 if ans:
1098 return ans
Martin v. Löwiscfe31282006-07-19 17:18:32 +00001099
Facundo Batista59c58842007-04-10 12:58:45 +00001100 # Must be infinite, and incrementing makes no difference
1101 return Decimal(self)
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00001102
1103 L = list(self._int)
1104 L[-1] += 1
1105 spot = len(L)-1
1106 while L[spot] == 10:
1107 L[spot] = 0
1108 if spot == 0:
1109 L[0:0] = [1]
1110 break
1111 L[spot-1] += 1
1112 spot -= 1
1113 ans = Decimal((self._sign, L, self._exp))
1114
Raymond Hettinger636a6b12004-09-19 01:54:09 +00001115 if context is None:
1116 context = getcontext()
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00001117 if round and context._rounding_decision == ALWAYS_ROUND:
Raymond Hettingerdab988d2004-10-09 07:10:44 +00001118 ans = ans._fix(context)
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00001119 return ans
1120
1121 def __mul__(self, other, context=None):
1122 """Return self * other.
1123
1124 (+-) INF * 0 (or its reverse) raise InvalidOperation.
1125 """
Raymond Hettinger636a6b12004-09-19 01:54:09 +00001126 other = _convert_other(other)
Raymond Hettinger267b8682005-03-27 10:47:39 +00001127 if other is NotImplemented:
1128 return other
Raymond Hettinger636a6b12004-09-19 01:54:09 +00001129
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00001130 if context is None:
1131 context = getcontext()
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00001132
Raymond Hettingerd87ac8f2004-07-09 10:52:54 +00001133 resultsign = self._sign ^ other._sign
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00001134
Raymond Hettinger636a6b12004-09-19 01:54:09 +00001135 if self._is_special or other._is_special:
1136 ans = self._check_nans(other, context)
1137 if ans:
1138 return ans
1139
1140 if self._isinfinity():
1141 if not other:
1142 return context._raise_error(InvalidOperation, '(+-)INF * 0')
1143 return Infsign[resultsign]
1144
1145 if other._isinfinity():
1146 if not self:
1147 return context._raise_error(InvalidOperation, '0 * (+-)INF')
1148 return Infsign[resultsign]
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00001149
1150 resultexp = self._exp + other._exp
1151 shouldround = context._rounding_decision == ALWAYS_ROUND
1152
1153 # Special case for multiplying by zero
1154 if not self or not other:
1155 ans = Decimal((resultsign, (0,), resultexp))
1156 if shouldround:
Facundo Batista59c58842007-04-10 12:58:45 +00001157 # Fixing in case the exponent is out of bounds
Raymond Hettingerdab988d2004-10-09 07:10:44 +00001158 ans = ans._fix(context)
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00001159 return ans
1160
1161 # Special case for multiplying by power of 10
1162 if self._int == (1,):
1163 ans = Decimal((resultsign, other._int, resultexp))
1164 if shouldround:
Raymond Hettingerdab988d2004-10-09 07:10:44 +00001165 ans = ans._fix(context)
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00001166 return ans
1167 if other._int == (1,):
1168 ans = Decimal((resultsign, self._int, resultexp))
1169 if shouldround:
Raymond Hettingerdab988d2004-10-09 07:10:44 +00001170 ans = ans._fix(context)
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00001171 return ans
1172
Raymond Hettinger636a6b12004-09-19 01:54:09 +00001173 op1 = _WorkRep(self)
1174 op2 = _WorkRep(other)
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00001175
Facundo Batista59c58842007-04-10 12:58:45 +00001176 ans = Decimal((resultsign, map(int, str(op1.int * op2.int)), resultexp))
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00001177 if shouldround:
Raymond Hettingerdab988d2004-10-09 07:10:44 +00001178 ans = ans._fix(context)
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00001179
1180 return ans
1181 __rmul__ = __mul__
1182
1183 def __div__(self, other, context=None):
1184 """Return self / other."""
1185 return self._divide(other, context=context)
1186 __truediv__ = __div__
1187
1188 def _divide(self, other, divmod = 0, context=None):
1189 """Return a / b, to context.prec precision.
1190
1191 divmod:
1192 0 => true division
1193 1 => (a //b, a%b)
1194 2 => a //b
1195 3 => a%b
1196
1197 Actually, if divmod is 2 or 3 a tuple is returned, but errors for
1198 computing the other value are not raised.
1199 """
Raymond Hettinger636a6b12004-09-19 01:54:09 +00001200 other = _convert_other(other)
Raymond Hettinger267b8682005-03-27 10:47:39 +00001201 if other is NotImplemented:
1202 if divmod in (0, 1):
1203 return NotImplemented
1204 return (NotImplemented, NotImplemented)
Raymond Hettinger636a6b12004-09-19 01:54:09 +00001205
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00001206 if context is None:
1207 context = getcontext()
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00001208
Raymond Hettingerd87ac8f2004-07-09 10:52:54 +00001209 sign = self._sign ^ other._sign
Raymond Hettinger636a6b12004-09-19 01:54:09 +00001210
1211 if self._is_special or other._is_special:
1212 ans = self._check_nans(other, context)
1213 if ans:
1214 if divmod:
1215 return (ans, ans)
1216 return ans
1217
1218 if self._isinfinity() and other._isinfinity():
1219 if divmod:
1220 return (context._raise_error(InvalidOperation,
1221 '(+-)INF // (+-)INF'),
1222 context._raise_error(InvalidOperation,
1223 '(+-)INF % (+-)INF'))
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00001224 return context._raise_error(InvalidOperation, '(+-)INF/(+-)INF')
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00001225
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00001226 if self._isinfinity():
1227 if divmod == 1:
1228 return (Infsign[sign],
1229 context._raise_error(InvalidOperation, 'INF % x'))
1230 elif divmod == 2:
1231 return (Infsign[sign], NaN)
1232 elif divmod == 3:
1233 return (Infsign[sign],
1234 context._raise_error(InvalidOperation, 'INF % x'))
Raymond Hettinger636a6b12004-09-19 01:54:09 +00001235 return Infsign[sign]
1236
1237 if other._isinfinity():
1238 if divmod:
1239 return (Decimal((sign, (0,), 0)), Decimal(self))
1240 context._raise_error(Clamped, 'Division by infinity')
1241 return Decimal((sign, (0,), context.Etiny()))
1242
1243 # Special cases for zeroes
1244 if not self and not other:
1245 if divmod:
1246 return context._raise_error(DivisionUndefined, '0 / 0', 1)
1247 return context._raise_error(DivisionUndefined, '0 / 0')
1248
1249 if not self:
1250 if divmod:
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00001251 otherside = Decimal(self)
1252 otherside._exp = min(self._exp, other._exp)
1253 return (Decimal((sign, (0,), 0)), otherside)
Raymond Hettinger636a6b12004-09-19 01:54:09 +00001254 exp = self._exp - other._exp
1255 if exp < context.Etiny():
1256 exp = context.Etiny()
1257 context._raise_error(Clamped, '0e-x / y')
1258 if exp > context.Emax:
1259 exp = context.Emax
1260 context._raise_error(Clamped, '0e+x / y')
1261 return Decimal( (sign, (0,), exp) )
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00001262
Raymond Hettinger636a6b12004-09-19 01:54:09 +00001263 if not other:
1264 if divmod:
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00001265 return context._raise_error(DivisionByZero, 'divmod(x,0)',
1266 sign, 1)
Raymond Hettinger636a6b12004-09-19 01:54:09 +00001267 return context._raise_error(DivisionByZero, 'x / 0', sign)
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00001268
Facundo Batista59c58842007-04-10 12:58:45 +00001269 # OK, so neither = 0, INF or NaN
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00001270 shouldround = context._rounding_decision == ALWAYS_ROUND
1271
Facundo Batista59c58842007-04-10 12:58:45 +00001272 # If we're dividing into ints, and self < other, stop.
1273 # self.__abs__(0) does not round.
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00001274 if divmod and (self.__abs__(0, context) < other.__abs__(0, context)):
1275
1276 if divmod == 1 or divmod == 3:
1277 exp = min(self._exp, other._exp)
1278 ans2 = self._rescale(exp, context=context, watchexp=0)
1279 if shouldround:
Raymond Hettingerdab988d2004-10-09 07:10:44 +00001280 ans2 = ans2._fix(context)
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00001281 return (Decimal( (sign, (0,), 0) ),
1282 ans2)
1283
1284 elif divmod == 2:
Facundo Batista59c58842007-04-10 12:58:45 +00001285 # Don't round the mod part, if we don't need it.
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00001286 return (Decimal( (sign, (0,), 0) ), Decimal(self))
1287
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00001288 op1 = _WorkRep(self)
1289 op2 = _WorkRep(other)
1290 op1, op2, adjust = _adjust_coefficients(op1, op2)
Raymond Hettinger636a6b12004-09-19 01:54:09 +00001291 res = _WorkRep( (sign, 0, (op1.exp - op2.exp)) )
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00001292 if divmod and res.exp > context.prec + 1:
1293 return context._raise_error(DivisionImpossible)
1294
Raymond Hettinger636a6b12004-09-19 01:54:09 +00001295 prec_limit = 10 ** context.prec
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00001296 while 1:
Raymond Hettinger636a6b12004-09-19 01:54:09 +00001297 while op2.int <= op1.int:
1298 res.int += 1
1299 op1.int -= op2.int
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00001300 if res.exp == 0 and divmod:
Raymond Hettinger636a6b12004-09-19 01:54:09 +00001301 if res.int >= prec_limit and shouldround:
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00001302 return context._raise_error(DivisionImpossible)
1303 otherside = Decimal(op1)
1304 frozen = context._ignore_all_flags()
1305
1306 exp = min(self._exp, other._exp)
Raymond Hettinger17931de2004-10-27 06:21:46 +00001307 otherside = otherside._rescale(exp, context=context, watchexp=0)
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00001308 context._regard_flags(*frozen)
1309 if shouldround:
Raymond Hettingerdab988d2004-10-09 07:10:44 +00001310 otherside = otherside._fix(context)
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00001311 return (Decimal(res), otherside)
1312
Raymond Hettinger636a6b12004-09-19 01:54:09 +00001313 if op1.int == 0 and adjust >= 0 and not divmod:
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00001314 break
Raymond Hettinger636a6b12004-09-19 01:54:09 +00001315 if res.int >= prec_limit and shouldround:
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00001316 if divmod:
1317 return context._raise_error(DivisionImpossible)
1318 shouldround=1
1319 # Really, the answer is a bit higher, so adding a one to
1320 # the end will make sure the rounding is right.
Raymond Hettinger636a6b12004-09-19 01:54:09 +00001321 if op1.int != 0:
1322 res.int *= 10
1323 res.int += 1
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00001324 res.exp -= 1
1325
1326 break
Raymond Hettinger636a6b12004-09-19 01:54:09 +00001327 res.int *= 10
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00001328 res.exp -= 1
1329 adjust += 1
Raymond Hettinger636a6b12004-09-19 01:54:09 +00001330 op1.int *= 10
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00001331 op1.exp -= 1
1332
Raymond Hettinger636a6b12004-09-19 01:54:09 +00001333 if res.exp == 0 and divmod and op2.int > op1.int:
Facundo Batista59c58842007-04-10 12:58:45 +00001334 # Solves an error in precision. Same as a previous block.
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00001335
Raymond Hettinger636a6b12004-09-19 01:54:09 +00001336 if res.int >= prec_limit and shouldround:
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00001337 return context._raise_error(DivisionImpossible)
1338 otherside = Decimal(op1)
1339 frozen = context._ignore_all_flags()
1340
1341 exp = min(self._exp, other._exp)
1342 otherside = otherside._rescale(exp, context=context)
1343
1344 context._regard_flags(*frozen)
1345
1346 return (Decimal(res), otherside)
1347
1348 ans = Decimal(res)
1349 if shouldround:
Raymond Hettingerdab988d2004-10-09 07:10:44 +00001350 ans = ans._fix(context)
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00001351 return ans
1352
1353 def __rdiv__(self, other, context=None):
1354 """Swaps self/other and returns __div__."""
Raymond Hettinger636a6b12004-09-19 01:54:09 +00001355 other = _convert_other(other)
Raymond Hettinger267b8682005-03-27 10:47:39 +00001356 if other is NotImplemented:
1357 return other
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00001358 return other.__div__(self, context=context)
1359 __rtruediv__ = __rdiv__
1360
1361 def __divmod__(self, other, context=None):
1362 """
1363 (self // other, self % other)
1364 """
1365 return self._divide(other, 1, context)
1366
1367 def __rdivmod__(self, other, context=None):
1368 """Swaps self/other and returns __divmod__."""
Raymond Hettinger636a6b12004-09-19 01:54:09 +00001369 other = _convert_other(other)
Raymond Hettinger267b8682005-03-27 10:47:39 +00001370 if other is NotImplemented:
1371 return other
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00001372 return other.__divmod__(self, context=context)
1373
1374 def __mod__(self, other, context=None):
1375 """
1376 self % other
1377 """
Raymond Hettinger636a6b12004-09-19 01:54:09 +00001378 other = _convert_other(other)
Raymond Hettinger267b8682005-03-27 10:47:39 +00001379 if other is NotImplemented:
1380 return other
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00001381
Raymond Hettinger636a6b12004-09-19 01:54:09 +00001382 if self._is_special or other._is_special:
1383 ans = self._check_nans(other, context)
1384 if ans:
1385 return ans
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00001386
1387 if self and not other:
1388 return context._raise_error(InvalidOperation, 'x % 0')
1389
1390 return self._divide(other, 3, context)[1]
1391
1392 def __rmod__(self, other, context=None):
1393 """Swaps self/other and returns __mod__."""
Raymond Hettinger636a6b12004-09-19 01:54:09 +00001394 other = _convert_other(other)
Raymond Hettinger267b8682005-03-27 10:47:39 +00001395 if other is NotImplemented:
1396 return other
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00001397 return other.__mod__(self, context=context)
1398
1399 def remainder_near(self, other, context=None):
1400 """
1401 Remainder nearest to 0- abs(remainder-near) <= other/2
1402 """
Raymond Hettinger636a6b12004-09-19 01:54:09 +00001403 other = _convert_other(other)
Raymond Hettinger267b8682005-03-27 10:47:39 +00001404 if other is NotImplemented:
1405 return other
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00001406
Raymond Hettinger636a6b12004-09-19 01:54:09 +00001407 if self._is_special or other._is_special:
1408 ans = self._check_nans(other, context)
1409 if ans:
1410 return ans
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00001411 if self and not other:
1412 return context._raise_error(InvalidOperation, 'x % 0')
1413
Raymond Hettinger636a6b12004-09-19 01:54:09 +00001414 if context is None:
1415 context = getcontext()
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00001416 # If DivisionImpossible causes an error, do not leave Rounded/Inexact
1417 # ignored in the calling function.
Raymond Hettinger9fce44b2004-08-08 04:03:24 +00001418 context = context._shallow_copy()
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00001419 flags = context._ignore_flags(Rounded, Inexact)
Facundo Batista59c58842007-04-10 12:58:45 +00001420 # Keep DivisionImpossible flags
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00001421 (side, r) = self.__divmod__(other, context=context)
1422
1423 if r._isnan():
1424 context._regard_flags(*flags)
1425 return r
1426
Raymond Hettinger9fce44b2004-08-08 04:03:24 +00001427 context = context._shallow_copy()
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00001428 rounding = context._set_rounding_decision(NEVER_ROUND)
1429
1430 if other._sign:
1431 comparison = other.__div__(Decimal(-2), context=context)
1432 else:
1433 comparison = other.__div__(Decimal(2), context=context)
1434
1435 context._set_rounding_decision(rounding)
1436 context._regard_flags(*flags)
1437
1438 s1, s2 = r._sign, comparison._sign
1439 r._sign, comparison._sign = 0, 0
1440
1441 if r < comparison:
1442 r._sign, comparison._sign = s1, s2
Facundo Batista59c58842007-04-10 12:58:45 +00001443 # Get flags now
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00001444 self.__divmod__(other, context=context)
Raymond Hettingerdab988d2004-10-09 07:10:44 +00001445 return r._fix(context)
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00001446 r._sign, comparison._sign = s1, s2
1447
1448 rounding = context._set_rounding_decision(NEVER_ROUND)
1449
1450 (side, r) = self.__divmod__(other, context=context)
1451 context._set_rounding_decision(rounding)
1452 if r._isnan():
1453 return r
1454
1455 decrease = not side._iseven()
1456 rounding = context._set_rounding_decision(NEVER_ROUND)
1457 side = side.__abs__(context=context)
1458 context._set_rounding_decision(rounding)
1459
1460 s1, s2 = r._sign, comparison._sign
1461 r._sign, comparison._sign = 0, 0
1462 if r > comparison or decrease and r == comparison:
1463 r._sign, comparison._sign = s1, s2
1464 context.prec += 1
Facundo Batista59c58842007-04-10 12:58:45 +00001465 numbsquant = len(side.__add__(Decimal(1), context=context)._int)
1466 if numbsquant >= context.prec:
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00001467 context.prec -= 1
1468 return context._raise_error(DivisionImpossible)[1]
1469 context.prec -= 1
1470 if self._sign == other._sign:
1471 r = r.__sub__(other, context=context)
1472 else:
1473 r = r.__add__(other, context=context)
1474 else:
1475 r._sign, comparison._sign = s1, s2
1476
Raymond Hettingerdab988d2004-10-09 07:10:44 +00001477 return r._fix(context)
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00001478
1479 def __floordiv__(self, other, context=None):
1480 """self // other"""
1481 return self._divide(other, 2, context)[0]
1482
1483 def __rfloordiv__(self, other, context=None):
1484 """Swaps self/other and returns __floordiv__."""
Raymond Hettinger636a6b12004-09-19 01:54:09 +00001485 other = _convert_other(other)
Raymond Hettinger267b8682005-03-27 10:47:39 +00001486 if other is NotImplemented:
1487 return other
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00001488 return other.__floordiv__(self, context=context)
1489
1490 def __float__(self):
1491 """Float representation."""
1492 return float(str(self))
1493
1494 def __int__(self):
Brett Cannon46b08022005-03-01 03:12:26 +00001495 """Converts self to an int, truncating if necessary."""
Raymond Hettinger636a6b12004-09-19 01:54:09 +00001496 if self._is_special:
1497 if self._isnan():
1498 context = getcontext()
1499 return context._raise_error(InvalidContext)
1500 elif self._isinfinity():
Facundo Batista59c58842007-04-10 12:58:45 +00001501 raise OverflowError("Cannot convert infinity to long")
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00001502 if self._exp >= 0:
Raymond Hettinger605ed022004-11-24 07:28:48 +00001503 s = ''.join(map(str, self._int)) + '0'*self._exp
1504 else:
1505 s = ''.join(map(str, self._int))[:self._exp]
1506 if s == '':
1507 s = '0'
1508 sign = '-'*self._sign
1509 return int(sign + s)
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00001510
1511 def __long__(self):
1512 """Converts to a long.
1513
1514 Equivalent to long(int(self))
1515 """
1516 return long(self.__int__())
1517
Raymond Hettingerdab988d2004-10-09 07:10:44 +00001518 def _fix(self, context):
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00001519 """Round if it is necessary to keep self within prec precision.
1520
1521 Rounds and fixes the exponent. Does not raise on a sNaN.
1522
1523 Arguments:
1524 self - Decimal instance
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00001525 context - context used.
1526 """
Raymond Hettinger636a6b12004-09-19 01:54:09 +00001527 if self._is_special:
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00001528 return self
1529 if context is None:
1530 context = getcontext()
Raymond Hettingerdab988d2004-10-09 07:10:44 +00001531 prec = context.prec
Facundo Batista99b55482004-10-26 23:38:46 +00001532 ans = self._fixexponents(context)
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00001533 if len(ans._int) > prec:
Raymond Hettingerdab988d2004-10-09 07:10:44 +00001534 ans = ans._round(prec, context=context)
Facundo Batista99b55482004-10-26 23:38:46 +00001535 ans = ans._fixexponents(context)
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00001536 return ans
1537
Facundo Batista99b55482004-10-26 23:38:46 +00001538 def _fixexponents(self, context):
Raymond Hettingerdab988d2004-10-09 07:10:44 +00001539 """Fix the exponents and return a copy with the exponent in bounds.
1540 Only call if known to not be a special value.
1541 """
1542 folddown = context._clamp
Raymond Hettinger636a6b12004-09-19 01:54:09 +00001543 Emin = context.Emin
Facundo Batista99b55482004-10-26 23:38:46 +00001544 ans = self
Raymond Hettinger636a6b12004-09-19 01:54:09 +00001545 ans_adjusted = ans.adjusted()
1546 if ans_adjusted < Emin:
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00001547 Etiny = context.Etiny()
1548 if ans._exp < Etiny:
1549 if not ans:
Facundo Batista99b55482004-10-26 23:38:46 +00001550 ans = Decimal(self)
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00001551 ans._exp = Etiny
1552 context._raise_error(Clamped)
1553 return ans
1554 ans = ans._rescale(Etiny, context=context)
Facundo Batista59c58842007-04-10 12:58:45 +00001555 # It isn't zero, and exp < Emin => subnormal
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00001556 context._raise_error(Subnormal)
1557 if context.flags[Inexact]:
1558 context._raise_error(Underflow)
1559 else:
1560 if ans:
Facundo Batista59c58842007-04-10 12:58:45 +00001561 # Only raise subnormal if non-zero.
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00001562 context._raise_error(Subnormal)
Raymond Hettinger636a6b12004-09-19 01:54:09 +00001563 else:
1564 Etop = context.Etop()
1565 if folddown and ans._exp > Etop:
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00001566 context._raise_error(Clamped)
Raymond Hettinger636a6b12004-09-19 01:54:09 +00001567 ans = ans._rescale(Etop, context=context)
1568 else:
1569 Emax = context.Emax
1570 if ans_adjusted > Emax:
1571 if not ans:
Facundo Batista99b55482004-10-26 23:38:46 +00001572 ans = Decimal(self)
Raymond Hettinger636a6b12004-09-19 01:54:09 +00001573 ans._exp = Emax
1574 context._raise_error(Clamped)
1575 return ans
1576 context._raise_error(Inexact)
1577 context._raise_error(Rounded)
Facundo Batista59c58842007-04-10 12:58:45 +00001578 c = context._raise_error(Overflow, 'above Emax', ans._sign)
1579 return c
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00001580 return ans
1581
1582 def _round(self, prec=None, rounding=None, context=None):
1583 """Returns a rounded version of self.
1584
1585 You can specify the precision or rounding method. Otherwise, the
1586 context determines it.
1587 """
1588
Raymond Hettinger636a6b12004-09-19 01:54:09 +00001589 if self._is_special:
1590 ans = self._check_nans(context=context)
1591 if ans:
1592 return ans
1593
1594 if self._isinfinity():
1595 return Decimal(self)
1596
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00001597 if context is None:
1598 context = getcontext()
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00001599
1600 if rounding is None:
1601 rounding = context.rounding
1602 if prec is None:
1603 prec = context.prec
1604
1605 if not self:
1606 if prec <= 0:
1607 dig = (0,)
1608 exp = len(self._int) - prec + self._exp
1609 else:
1610 dig = (0,) * prec
1611 exp = len(self._int) + self._exp - prec
1612 ans = Decimal((self._sign, dig, exp))
1613 context._raise_error(Rounded)
1614 return ans
1615
1616 if prec == 0:
1617 temp = Decimal(self)
1618 temp._int = (0,)+temp._int
1619 prec = 1
1620 elif prec < 0:
1621 exp = self._exp + len(self._int) - prec - 1
1622 temp = Decimal( (self._sign, (0, 1), exp))
1623 prec = 1
1624 else:
1625 temp = Decimal(self)
1626
1627 numdigits = len(temp._int)
1628 if prec == numdigits:
1629 return temp
1630
1631 # See if we need to extend precision
1632 expdiff = prec - numdigits
1633 if expdiff > 0:
1634 tmp = list(temp._int)
1635 tmp.extend([0] * expdiff)
1636 ans = Decimal( (temp._sign, tmp, temp._exp - expdiff))
1637 return ans
1638
Facundo Batista59c58842007-04-10 12:58:45 +00001639 # OK, but maybe all the lost digits are 0.
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00001640 lostdigits = self._int[expdiff:]
1641 if lostdigits == (0,) * len(lostdigits):
1642 ans = Decimal( (temp._sign, temp._int[:prec], temp._exp - expdiff))
Facundo Batista59c58842007-04-10 12:58:45 +00001643 # Rounded, but not Inexact
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00001644 context._raise_error(Rounded)
1645 return ans
1646
1647 # Okay, let's round and lose data
1648
1649 this_function = getattr(temp, self._pick_rounding_function[rounding])
Facundo Batista59c58842007-04-10 12:58:45 +00001650 # Now we've got the rounding function
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00001651
1652 if prec != context.prec:
Raymond Hettinger9fce44b2004-08-08 04:03:24 +00001653 context = context._shallow_copy()
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00001654 context.prec = prec
1655 ans = this_function(prec, expdiff, context)
1656 context._raise_error(Rounded)
1657 context._raise_error(Inexact, 'Changed in rounding')
1658
1659 return ans
1660
1661 _pick_rounding_function = {}
1662
1663 def _round_down(self, prec, expdiff, context):
1664 """Also known as round-towards-0, truncate."""
1665 return Decimal( (self._sign, self._int[:prec], self._exp - expdiff) )
1666
1667 def _round_half_up(self, prec, expdiff, context, tmp = None):
1668 """Rounds 5 up (away from 0)"""
1669
1670 if tmp is None:
1671 tmp = Decimal( (self._sign,self._int[:prec], self._exp - expdiff))
1672 if self._int[prec] >= 5:
1673 tmp = tmp._increment(round=0, context=context)
1674 if len(tmp._int) > prec:
1675 return Decimal( (tmp._sign, tmp._int[:-1], tmp._exp + 1))
1676 return tmp
1677
1678 def _round_half_even(self, prec, expdiff, context):
1679 """Round 5 to even, rest to nearest."""
1680
1681 tmp = Decimal( (self._sign, self._int[:prec], self._exp - expdiff))
1682 half = (self._int[prec] == 5)
1683 if half:
1684 for digit in self._int[prec+1:]:
1685 if digit != 0:
1686 half = 0
1687 break
1688 if half:
Raymond Hettinger61992ef2004-08-06 23:42:16 +00001689 if self._int[prec-1] & 1 == 0:
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00001690 return tmp
1691 return self._round_half_up(prec, expdiff, context, tmp)
1692
1693 def _round_half_down(self, prec, expdiff, context):
1694 """Round 5 down"""
1695
1696 tmp = Decimal( (self._sign, self._int[:prec], self._exp - expdiff))
1697 half = (self._int[prec] == 5)
1698 if half:
1699 for digit in self._int[prec+1:]:
1700 if digit != 0:
1701 half = 0
1702 break
1703 if half:
1704 return tmp
1705 return self._round_half_up(prec, expdiff, context, tmp)
1706
1707 def _round_up(self, prec, expdiff, context):
1708 """Rounds away from 0."""
1709 tmp = Decimal( (self._sign, self._int[:prec], self._exp - expdiff) )
1710 for digit in self._int[prec:]:
1711 if digit != 0:
1712 tmp = tmp._increment(round=1, context=context)
1713 if len(tmp._int) > prec:
1714 return Decimal( (tmp._sign, tmp._int[:-1], tmp._exp + 1))
1715 else:
1716 return tmp
1717 return tmp
1718
1719 def _round_ceiling(self, prec, expdiff, context):
1720 """Rounds up (not away from 0 if negative.)"""
1721 if self._sign:
1722 return self._round_down(prec, expdiff, context)
1723 else:
1724 return self._round_up(prec, expdiff, context)
1725
1726 def _round_floor(self, prec, expdiff, context):
1727 """Rounds down (not towards 0 if negative)"""
1728 if not self._sign:
1729 return self._round_down(prec, expdiff, context)
1730 else:
1731 return self._round_up(prec, expdiff, context)
1732
1733 def __pow__(self, n, modulo = None, context=None):
1734 """Return self ** n (mod modulo)
1735
1736 If modulo is None (default), don't take it mod modulo.
1737 """
Raymond Hettinger636a6b12004-09-19 01:54:09 +00001738 n = _convert_other(n)
Raymond Hettinger267b8682005-03-27 10:47:39 +00001739 if n is NotImplemented:
1740 return n
Raymond Hettinger636a6b12004-09-19 01:54:09 +00001741
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00001742 if context is None:
1743 context = getcontext()
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00001744
Raymond Hettinger636a6b12004-09-19 01:54:09 +00001745 if self._is_special or n._is_special or n.adjusted() > 8:
Facundo Batista59c58842007-04-10 12:58:45 +00001746 # Because the spot << doesn't work with really big exponents
Raymond Hettinger636a6b12004-09-19 01:54:09 +00001747 if n._isinfinity() or n.adjusted() > 8:
1748 return context._raise_error(InvalidOperation, 'x ** INF')
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00001749
Raymond Hettinger636a6b12004-09-19 01:54:09 +00001750 ans = self._check_nans(n, context)
1751 if ans:
1752 return ans
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00001753
Raymond Hettinger636a6b12004-09-19 01:54:09 +00001754 if not n._isinteger():
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00001755 return context._raise_error(InvalidOperation, 'x ** (non-integer)')
1756
1757 if not self and not n:
1758 return context._raise_error(InvalidOperation, '0 ** 0')
1759
1760 if not n:
1761 return Decimal(1)
1762
1763 if self == Decimal(1):
1764 return Decimal(1)
1765
1766 sign = self._sign and not n._iseven()
1767 n = int(n)
1768
1769 if self._isinfinity():
1770 if modulo:
1771 return context._raise_error(InvalidOperation, 'INF % x')
1772 if n > 0:
1773 return Infsign[sign]
1774 return Decimal( (sign, (0,), 0) )
1775
Facundo Batista59c58842007-04-10 12:58:45 +00001776 # With ludicrously large exponent, just raise an overflow
1777 # and return inf.
1778 if not modulo and n > 0 and \
1779 (self._exp + len(self._int) - 1) * n > context.Emax and self:
Martin v. Löwiscfe31282006-07-19 17:18:32 +00001780
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00001781 tmp = Decimal('inf')
1782 tmp._sign = sign
1783 context._raise_error(Rounded)
1784 context._raise_error(Inexact)
1785 context._raise_error(Overflow, 'Big power', sign)
1786 return tmp
1787
1788 elength = len(str(abs(n)))
1789 firstprec = context.prec
1790
Raymond Hettinger99148e72004-07-14 19:56:56 +00001791 if not modulo and firstprec + elength + 1 > DefaultContext.Emax:
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00001792 return context._raise_error(Overflow, 'Too much precision.', sign)
1793
1794 mul = Decimal(self)
1795 val = Decimal(1)
Raymond Hettinger9fce44b2004-08-08 04:03:24 +00001796 context = context._shallow_copy()
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00001797 context.prec = firstprec + elength + 1
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00001798 if n < 0:
Facundo Batista59c58842007-04-10 12:58:45 +00001799 # n is a long now, not Decimal instance
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00001800 n = -n
1801 mul = Decimal(1).__div__(mul, context=context)
1802
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00001803 spot = 1
1804 while spot <= n:
1805 spot <<= 1
1806
1807 spot >>= 1
Facundo Batista59c58842007-04-10 12:58:45 +00001808 # spot is the highest power of 2 less than n
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00001809 while spot:
1810 val = val.__mul__(val, context=context)
1811 if val._isinfinity():
1812 val = Infsign[sign]
1813 break
1814 if spot & n:
1815 val = val.__mul__(mul, context=context)
1816 if modulo is not None:
1817 val = val.__mod__(modulo, context=context)
1818 spot >>= 1
1819 context.prec = firstprec
1820
Raymond Hettinger76e60d62004-10-20 06:58:28 +00001821 if context._rounding_decision == ALWAYS_ROUND:
Raymond Hettingerdab988d2004-10-09 07:10:44 +00001822 return val._fix(context)
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00001823 return val
1824
1825 def __rpow__(self, other, context=None):
1826 """Swaps self/other and returns __pow__."""
Raymond Hettinger636a6b12004-09-19 01:54:09 +00001827 other = _convert_other(other)
Raymond Hettinger267b8682005-03-27 10:47:39 +00001828 if other is NotImplemented:
1829 return other
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00001830 return other.__pow__(self, context=context)
1831
1832 def normalize(self, context=None):
1833 """Normalize- strip trailing 0s, change anything equal to 0 to 0e0"""
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00001834
Raymond Hettinger636a6b12004-09-19 01:54:09 +00001835 if self._is_special:
1836 ans = self._check_nans(context=context)
1837 if ans:
1838 return ans
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00001839
Raymond Hettingerdab988d2004-10-09 07:10:44 +00001840 dup = self._fix(context)
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00001841 if dup._isinfinity():
1842 return dup
1843
1844 if not dup:
1845 return Decimal( (dup._sign, (0,), 0) )
1846 end = len(dup._int)
1847 exp = dup._exp
1848 while dup._int[end-1] == 0:
1849 exp += 1
1850 end -= 1
1851 return Decimal( (dup._sign, dup._int[:end], exp) )
1852
1853
Raymond Hettingerdab988d2004-10-09 07:10:44 +00001854 def quantize(self, exp, rounding=None, context=None, watchexp=1):
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00001855 """Quantize self so its exponent is the same as that of exp.
1856
1857 Similar to self._rescale(exp._exp) but with error checking.
1858 """
Raymond Hettinger636a6b12004-09-19 01:54:09 +00001859 if self._is_special or exp._is_special:
1860 ans = self._check_nans(exp, context)
1861 if ans:
1862 return ans
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00001863
Raymond Hettinger636a6b12004-09-19 01:54:09 +00001864 if exp._isinfinity() or self._isinfinity():
1865 if exp._isinfinity() and self._isinfinity():
Facundo Batista59c58842007-04-10 12:58:45 +00001866 return self # if both are inf, it is OK
Raymond Hettinger636a6b12004-09-19 01:54:09 +00001867 if context is None:
1868 context = getcontext()
1869 return context._raise_error(InvalidOperation,
1870 'quantize with one INF')
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00001871 return self._rescale(exp._exp, rounding, context, watchexp)
1872
1873 def same_quantum(self, other):
1874 """Test whether self and other have the same exponent.
1875
1876 same as self._exp == other._exp, except NaN == sNaN
1877 """
Raymond Hettinger636a6b12004-09-19 01:54:09 +00001878 if self._is_special or other._is_special:
1879 if self._isnan() or other._isnan():
1880 return self._isnan() and other._isnan() and True
1881 if self._isinfinity() or other._isinfinity():
1882 return self._isinfinity() and other._isinfinity() and True
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00001883 return self._exp == other._exp
1884
Raymond Hettingerdab988d2004-10-09 07:10:44 +00001885 def _rescale(self, exp, rounding=None, context=None, watchexp=1):
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00001886 """Rescales so that the exponent is exp.
1887
1888 exp = exp to scale to (an integer)
1889 rounding = rounding version
1890 watchexp: if set (default) an error is returned if exp is greater
1891 than Emax or less than Etiny.
1892 """
1893 if context is None:
1894 context = getcontext()
1895
Raymond Hettinger636a6b12004-09-19 01:54:09 +00001896 if self._is_special:
1897 if self._isinfinity():
Martin v. Löwiscfe31282006-07-19 17:18:32 +00001898 return context._raise_error(InvalidOperation, 'rescale with an INF')
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00001899
Raymond Hettinger636a6b12004-09-19 01:54:09 +00001900 ans = self._check_nans(context=context)
1901 if ans:
1902 return ans
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00001903
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00001904 if watchexp and (context.Emax < exp or context.Etiny() > exp):
1905 return context._raise_error(InvalidOperation, 'rescale(a, INF)')
1906
1907 if not self:
1908 ans = Decimal(self)
1909 ans._int = (0,)
1910 ans._exp = exp
1911 return ans
1912
1913 diff = self._exp - exp
Raymond Hettingerdab988d2004-10-09 07:10:44 +00001914 digits = len(self._int) + diff
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00001915
1916 if watchexp and digits > context.prec:
1917 return context._raise_error(InvalidOperation, 'Rescale > prec')
1918
1919 tmp = Decimal(self)
Raymond Hettingerdab988d2004-10-09 07:10:44 +00001920 tmp._int = (0,) + tmp._int
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00001921 digits += 1
1922
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00001923 if digits < 0:
1924 tmp._exp = -digits + tmp._exp
1925 tmp._int = (0,1)
1926 digits = 1
1927 tmp = tmp._round(digits, rounding, context=context)
1928
1929 if tmp._int[0] == 0 and len(tmp._int) > 1:
1930 tmp._int = tmp._int[1:]
1931 tmp._exp = exp
1932
Raymond Hettinger636a6b12004-09-19 01:54:09 +00001933 tmp_adjusted = tmp.adjusted()
1934 if tmp and tmp_adjusted < context.Emin:
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00001935 context._raise_error(Subnormal)
Raymond Hettinger636a6b12004-09-19 01:54:09 +00001936 elif tmp and tmp_adjusted > context.Emax:
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00001937 return context._raise_error(InvalidOperation, 'rescale(a, INF)')
1938 return tmp
1939
Raymond Hettingerdab988d2004-10-09 07:10:44 +00001940 def to_integral(self, rounding=None, context=None):
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00001941 """Rounds to the nearest integer, without raising inexact, rounded."""
Raymond Hettinger636a6b12004-09-19 01:54:09 +00001942 if self._is_special:
1943 ans = self._check_nans(context=context)
1944 if ans:
1945 return ans
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00001946 if self._exp >= 0:
1947 return self
Raymond Hettinger636a6b12004-09-19 01:54:09 +00001948 if context is None:
1949 context = getcontext()
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00001950 flags = context._ignore_flags(Rounded, Inexact)
1951 ans = self._rescale(0, rounding, context=context)
1952 context._regard_flags(flags)
1953 return ans
1954
1955 def sqrt(self, context=None):
1956 """Return the square root of self.
1957
1958 Uses a converging algorithm (Xn+1 = 0.5*(Xn + self / Xn))
1959 Should quadratically approach the right answer.
1960 """
Raymond Hettinger636a6b12004-09-19 01:54:09 +00001961 if self._is_special:
1962 ans = self._check_nans(context=context)
1963 if ans:
1964 return ans
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00001965
Raymond Hettinger636a6b12004-09-19 01:54:09 +00001966 if self._isinfinity() and self._sign == 0:
1967 return Decimal(self)
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00001968
1969 if not self:
Facundo Batista59c58842007-04-10 12:58:45 +00001970 # exponent = self._exp / 2, using round_down.
1971 # if self._exp < 0:
Martin v. Löwiscfe31282006-07-19 17:18:32 +00001972 # exp = (self._exp+1) // 2
Facundo Batista59c58842007-04-10 12:58:45 +00001973 # else:
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00001974 exp = (self._exp) // 2
1975 if self._sign == 1:
Facundo Batista59c58842007-04-10 12:58:45 +00001976 # sqrt(-0) = -0
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00001977 return Decimal( (1, (0,), exp))
1978 else:
1979 return Decimal( (0, (0,), exp))
1980
Raymond Hettinger636a6b12004-09-19 01:54:09 +00001981 if context is None:
1982 context = getcontext()
1983
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00001984 if self._sign == 1:
1985 return context._raise_error(InvalidOperation, 'sqrt(-x), x > 0')
1986
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00001987 tmp = Decimal(self)
1988
Raymond Hettinger4837a222004-09-27 14:23:40 +00001989 expadd = tmp._exp // 2
Raymond Hettinger61992ef2004-08-06 23:42:16 +00001990 if tmp._exp & 1:
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00001991 tmp._int += (0,)
1992 tmp._exp = 0
1993 else:
1994 tmp._exp = 0
1995
Raymond Hettinger9fce44b2004-08-08 04:03:24 +00001996 context = context._shallow_copy()
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00001997 flags = context._ignore_all_flags()
1998 firstprec = context.prec
1999 context.prec = 3
Raymond Hettinger61992ef2004-08-06 23:42:16 +00002000 if tmp.adjusted() & 1 == 0:
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00002001 ans = Decimal( (0, (8,1,9), tmp.adjusted() - 2) )
2002 ans = ans.__add__(tmp.__mul__(Decimal((0, (2,5,9), -2)),
2003 context=context), context=context)
Raymond Hettinger4837a222004-09-27 14:23:40 +00002004 ans._exp -= 1 + tmp.adjusted() // 2
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00002005 else:
2006 ans = Decimal( (0, (2,5,9), tmp._exp + len(tmp._int)- 3) )
2007 ans = ans.__add__(tmp.__mul__(Decimal((0, (8,1,9), -3)),
2008 context=context), context=context)
Raymond Hettinger4837a222004-09-27 14:23:40 +00002009 ans._exp -= 1 + tmp.adjusted() // 2
Martin v. Löwiscfe31282006-07-19 17:18:32 +00002010
Facundo Batista59c58842007-04-10 12:58:45 +00002011 # ans is now a linear approximation.
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00002012 Emax, Emin = context.Emax, context.Emin
Raymond Hettinger99148e72004-07-14 19:56:56 +00002013 context.Emax, context.Emin = DefaultContext.Emax, DefaultContext.Emin
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00002014
2015 half = Decimal('0.5')
2016
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00002017 maxp = firstprec + 2
2018 rounding = context._set_rounding(ROUND_HALF_EVEN)
2019 while 1:
2020 context.prec = min(2*context.prec - 2, maxp)
2021 ans = half.__mul__(ans.__add__(tmp.__div__(ans, context=context),
2022 context=context), context=context)
2023 if context.prec == maxp:
2024 break
2025
Facundo Batista59c58842007-04-10 12:58:45 +00002026 # Round to the answer's precision-- the only error can be 1 ulp.
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00002027 context.prec = firstprec
2028 prevexp = ans.adjusted()
2029 ans = ans._round(context=context)
2030
Facundo Batista59c58842007-04-10 12:58:45 +00002031 # Now, check if the other last digits are better.
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00002032 context.prec = firstprec + 1
2033 # In case we rounded up another digit and we should actually go lower.
2034 if prevexp != ans.adjusted():
2035 ans._int += (0,)
2036 ans._exp -= 1
2037
2038
2039 lower = ans.__sub__(Decimal((0, (5,), ans._exp-1)), context=context)
2040 context._set_rounding(ROUND_UP)
2041 if lower.__mul__(lower, context=context) > (tmp):
2042 ans = ans.__sub__(Decimal((0, (1,), ans._exp)), context=context)
2043
2044 else:
2045 upper = ans.__add__(Decimal((0, (5,), ans._exp-1)),context=context)
2046 context._set_rounding(ROUND_DOWN)
2047 if upper.__mul__(upper, context=context) < tmp:
2048 ans = ans.__add__(Decimal((0, (1,), ans._exp)),context=context)
2049
2050 ans._exp += expadd
2051
2052 context.prec = firstprec
2053 context.rounding = rounding
Raymond Hettingerdab988d2004-10-09 07:10:44 +00002054 ans = ans._fix(context)
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00002055
2056 rounding = context._set_rounding_decision(NEVER_ROUND)
2057 if not ans.__mul__(ans, context=context) == self:
2058 # Only rounded/inexact if here.
2059 context._regard_flags(flags)
2060 context._raise_error(Rounded)
2061 context._raise_error(Inexact)
2062 else:
Facundo Batista59c58842007-04-10 12:58:45 +00002063 # Exact answer, so let's set the exponent right.
2064 # if self._exp < 0:
Martin v. Löwiscfe31282006-07-19 17:18:32 +00002065 # exp = (self._exp +1)// 2
Facundo Batista59c58842007-04-10 12:58:45 +00002066 # else:
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00002067 exp = self._exp // 2
2068 context.prec += ans._exp - exp
2069 ans = ans._rescale(exp, context=context)
2070 context.prec = firstprec
2071 context._regard_flags(flags)
2072 context.Emax, context.Emin = Emax, Emin
2073
Raymond Hettingerdab988d2004-10-09 07:10:44 +00002074 return ans._fix(context)
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00002075
2076 def max(self, other, context=None):
2077 """Returns the larger value.
2078
2079 like max(self, other) except if one is not a number, returns
2080 NaN (and signals if one is sNaN). Also rounds.
2081 """
Raymond Hettinger636a6b12004-09-19 01:54:09 +00002082 other = _convert_other(other)
Raymond Hettinger267b8682005-03-27 10:47:39 +00002083 if other is NotImplemented:
2084 return other
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00002085
Raymond Hettinger636a6b12004-09-19 01:54:09 +00002086 if self._is_special or other._is_special:
Facundo Batista59c58842007-04-10 12:58:45 +00002087 # If one operand is a quiet NaN and the other is number, then the
Raymond Hettinger636a6b12004-09-19 01:54:09 +00002088 # number is always returned
2089 sn = self._isnan()
2090 on = other._isnan()
2091 if sn or on:
2092 if on == 1 and sn != 2:
2093 return self
2094 if sn == 1 and on != 2:
2095 return other
2096 return self._check_nans(other, context)
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00002097
2098 ans = self
Raymond Hettingerd6c700a2004-08-17 06:39:37 +00002099 c = self.__cmp__(other)
2100 if c == 0:
Facundo Batista59c58842007-04-10 12:58:45 +00002101 # If both operands are finite and equal in numerical value
Raymond Hettingerd6c700a2004-08-17 06:39:37 +00002102 # then an ordering is applied:
2103 #
Facundo Batista59c58842007-04-10 12:58:45 +00002104 # If the signs differ then max returns the operand with the
Raymond Hettingerd6c700a2004-08-17 06:39:37 +00002105 # positive sign and min returns the operand with the negative sign
2106 #
Facundo Batista59c58842007-04-10 12:58:45 +00002107 # If the signs are the same then the exponent is used to select
Raymond Hettingerd6c700a2004-08-17 06:39:37 +00002108 # the result.
2109 if self._sign != other._sign:
2110 if self._sign:
2111 ans = other
2112 elif self._exp < other._exp and not self._sign:
2113 ans = other
2114 elif self._exp > other._exp and self._sign:
2115 ans = other
2116 elif c == -1:
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00002117 ans = other
Raymond Hettinger636a6b12004-09-19 01:54:09 +00002118
2119 if context is None:
2120 context = getcontext()
Raymond Hettinger76e60d62004-10-20 06:58:28 +00002121 if context._rounding_decision == ALWAYS_ROUND:
2122 return ans._fix(context)
2123 return ans
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00002124
2125 def min(self, other, context=None):
2126 """Returns the smaller value.
2127
Facundo Batista59c58842007-04-10 12:58:45 +00002128 Like min(self, other) except if one is not a number, returns
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00002129 NaN (and signals if one is sNaN). Also rounds.
2130 """
Raymond Hettinger636a6b12004-09-19 01:54:09 +00002131 other = _convert_other(other)
Raymond Hettinger267b8682005-03-27 10:47:39 +00002132 if other is NotImplemented:
2133 return other
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00002134
Raymond Hettinger636a6b12004-09-19 01:54:09 +00002135 if self._is_special or other._is_special:
Facundo Batista59c58842007-04-10 12:58:45 +00002136 # If one operand is a quiet NaN and the other is number, then the
Raymond Hettinger636a6b12004-09-19 01:54:09 +00002137 # number is always returned
2138 sn = self._isnan()
2139 on = other._isnan()
2140 if sn or on:
2141 if on == 1 and sn != 2:
2142 return self
2143 if sn == 1 and on != 2:
2144 return other
2145 return self._check_nans(other, context)
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00002146
2147 ans = self
Raymond Hettingerd6c700a2004-08-17 06:39:37 +00002148 c = self.__cmp__(other)
2149 if c == 0:
Facundo Batista59c58842007-04-10 12:58:45 +00002150 # If both operands are finite and equal in numerical value
Raymond Hettingerd6c700a2004-08-17 06:39:37 +00002151 # then an ordering is applied:
2152 #
Facundo Batista59c58842007-04-10 12:58:45 +00002153 # If the signs differ then max returns the operand with the
Raymond Hettingerd6c700a2004-08-17 06:39:37 +00002154 # positive sign and min returns the operand with the negative sign
2155 #
Facundo Batista59c58842007-04-10 12:58:45 +00002156 # If the signs are the same then the exponent is used to select
Raymond Hettingerd6c700a2004-08-17 06:39:37 +00002157 # the result.
2158 if self._sign != other._sign:
2159 if other._sign:
2160 ans = other
2161 elif self._exp > other._exp and not self._sign:
2162 ans = other
2163 elif self._exp < other._exp and self._sign:
2164 ans = other
2165 elif c == 1:
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00002166 ans = other
Raymond Hettinger636a6b12004-09-19 01:54:09 +00002167
2168 if context is None:
2169 context = getcontext()
Raymond Hettinger76e60d62004-10-20 06:58:28 +00002170 if context._rounding_decision == ALWAYS_ROUND:
2171 return ans._fix(context)
2172 return ans
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00002173
2174 def _isinteger(self):
2175 """Returns whether self is an integer"""
2176 if self._exp >= 0:
2177 return True
2178 rest = self._int[self._exp:]
2179 return rest == (0,)*len(rest)
2180
2181 def _iseven(self):
2182 """Returns 1 if self is even. Assumes self is an integer."""
2183 if self._exp > 0:
2184 return 1
Raymond Hettinger61992ef2004-08-06 23:42:16 +00002185 return self._int[-1+self._exp] & 1 == 0
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00002186
2187 def adjusted(self):
2188 """Return the adjusted exponent of self"""
2189 try:
2190 return self._exp + len(self._int) - 1
Facundo Batista59c58842007-04-10 12:58:45 +00002191 # If NaN or Infinity, self._exp is string
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00002192 except TypeError:
2193 return 0
2194
Facundo Batista59c58842007-04-10 12:58:45 +00002195 # Support for pickling, copy, and deepcopy
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00002196 def __reduce__(self):
2197 return (self.__class__, (str(self),))
2198
2199 def __copy__(self):
2200 if type(self) == Decimal:
Martin v. Löwiscfe31282006-07-19 17:18:32 +00002201 return self # I'm immutable; therefore I am my own clone
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00002202 return self.__class__(str(self))
2203
2204 def __deepcopy__(self, memo):
2205 if type(self) == Decimal:
Martin v. Löwiscfe31282006-07-19 17:18:32 +00002206 return self # My components are also immutable
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00002207 return self.__class__(str(self))
2208
Facundo Batista59c58842007-04-10 12:58:45 +00002209##### Context class #######################################################
Raymond Hettingerd9c0a7a2004-07-03 10:02:28 +00002210
Martin v. Löwiscfe31282006-07-19 17:18:32 +00002211
2212# get rounding method function:
Facundo Batista59c58842007-04-10 12:58:45 +00002213rounding_functions = [name for name in Decimal.__dict__.keys()
2214 if name.startswith('_round_')]
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00002215for name in rounding_functions:
Facundo Batista59c58842007-04-10 12:58:45 +00002216 # name is like _round_half_even, goes to the global ROUND_HALF_EVEN value.
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00002217 globalname = name[1:].upper()
2218 val = globals()[globalname]
2219 Decimal._pick_rounding_function[val] = name
2220
Raymond Hettinger9ec3e3b2004-07-03 13:48:56 +00002221del name, val, globalname, rounding_functions
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00002222
Nick Coghlanced12182006-09-02 03:54:17 +00002223class _ContextManager(object):
Nick Coghlan8b6999b2006-08-31 12:00:43 +00002224 """Context manager class to support localcontext().
Guido van Rossum1a5e21e2006-02-28 21:57:43 +00002225
Nick Coghlanced12182006-09-02 03:54:17 +00002226 Sets a copy of the supplied context in __enter__() and restores
Nick Coghlan8b6999b2006-08-31 12:00:43 +00002227 the previous decimal context in __exit__()
Guido van Rossum1a5e21e2006-02-28 21:57:43 +00002228 """
2229 def __init__(self, new_context):
Nick Coghlanced12182006-09-02 03:54:17 +00002230 self.new_context = new_context.copy()
Guido van Rossum1a5e21e2006-02-28 21:57:43 +00002231 def __enter__(self):
2232 self.saved_context = getcontext()
2233 setcontext(self.new_context)
2234 return self.new_context
2235 def __exit__(self, t, v, tb):
2236 setcontext(self.saved_context)
Guido van Rossum1a5e21e2006-02-28 21:57:43 +00002237
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00002238class Context(object):
2239 """Contains the context for a Decimal instance.
2240
2241 Contains:
2242 prec - precision (for use in rounding, division, square roots..)
Facundo Batista59c58842007-04-10 12:58:45 +00002243 rounding - rounding type (how you round)
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00002244 _rounding_decision - ALWAYS_ROUND, NEVER_ROUND -- do you round?
Raymond Hettingerbf440692004-07-10 14:14:37 +00002245 traps - If traps[exception] = 1, then the exception is
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00002246 raised when it is caused. Otherwise, a value is
2247 substituted in.
2248 flags - When an exception is caused, flags[exception] is incremented.
2249 (Whether or not the trap_enabler is set)
2250 Should be reset by user of Decimal instance.
Raymond Hettinger0ea241e2004-07-04 13:53:24 +00002251 Emin - Minimum exponent
2252 Emax - Maximum exponent
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00002253 capitals - If 1, 1*10^1 is printed as 1E+1.
2254 If 0, printed as 1e1
Raymond Hettingere0f15812004-07-05 05:36:39 +00002255 _clamp - If 1, change exponents if too high (Default 0)
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00002256 """
Raymond Hettinger9ec3e3b2004-07-03 13:48:56 +00002257
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00002258 def __init__(self, prec=None, rounding=None,
Raymond Hettingerabf8a562004-10-12 09:12:16 +00002259 traps=None, flags=None,
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00002260 _rounding_decision=None,
Raymond Hettinger0ea241e2004-07-04 13:53:24 +00002261 Emin=None, Emax=None,
Raymond Hettingere0f15812004-07-05 05:36:39 +00002262 capitals=None, _clamp=0,
Raymond Hettingerabf8a562004-10-12 09:12:16 +00002263 _ignored_flags=None):
2264 if flags is None:
2265 flags = []
2266 if _ignored_flags is None:
2267 _ignored_flags = []
Raymond Hettingerbf440692004-07-10 14:14:37 +00002268 if not isinstance(flags, dict):
Raymond Hettingerfed52962004-07-14 15:41:57 +00002269 flags = dict([(s,s in flags) for s in _signals])
Raymond Hettingerb91af522004-07-14 16:35:30 +00002270 del s
Raymond Hettingerbf440692004-07-10 14:14:37 +00002271 if traps is not None and not isinstance(traps, dict):
Raymond Hettingerfed52962004-07-14 15:41:57 +00002272 traps = dict([(s,s in traps) for s in _signals])
Raymond Hettingerb91af522004-07-14 16:35:30 +00002273 del s
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00002274 for name, val in locals().items():
2275 if val is None:
Raymond Hettingereb260842005-06-07 18:52:34 +00002276 setattr(self, name, _copy.copy(getattr(DefaultContext, name)))
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00002277 else:
2278 setattr(self, name, val)
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00002279 del self.self
2280
Raymond Hettingerb1b605e2004-07-04 01:55:39 +00002281 def __repr__(self):
Raymond Hettingerbf440692004-07-10 14:14:37 +00002282 """Show the current context."""
Raymond Hettingerb1b605e2004-07-04 01:55:39 +00002283 s = []
Facundo Batista59c58842007-04-10 12:58:45 +00002284 s.append('Context(prec=%(prec)d, rounding=%(rounding)s, '
2285 'Emin=%(Emin)d, Emax=%(Emax)d, capitals=%(capitals)d'
2286 % vars(self))
2287 names = [f.__name__ for f, v in self.flags.items() if v]
2288 s.append('flags=[' + ', '.join(names) + ']')
2289 names = [t.__name__ for t, v in self.traps.items() if v]
2290 s.append('traps=[' + ', '.join(names) + ']')
Raymond Hettingerb1b605e2004-07-04 01:55:39 +00002291 return ', '.join(s) + ')'
2292
Raymond Hettingerd9c0a7a2004-07-03 10:02:28 +00002293 def clear_flags(self):
2294 """Reset all flags to zero"""
2295 for flag in self.flags:
Raymond Hettingerb1b605e2004-07-04 01:55:39 +00002296 self.flags[flag] = 0
Raymond Hettingerd9c0a7a2004-07-03 10:02:28 +00002297
Raymond Hettinger9fce44b2004-08-08 04:03:24 +00002298 def _shallow_copy(self):
2299 """Returns a shallow copy from self."""
Raymond Hettingerbf440692004-07-10 14:14:37 +00002300 nc = Context(self.prec, self.rounding, self.traps, self.flags,
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00002301 self._rounding_decision, self.Emin, self.Emax,
2302 self.capitals, self._clamp, self._ignored_flags)
2303 return nc
Raymond Hettinger9fce44b2004-08-08 04:03:24 +00002304
2305 def copy(self):
2306 """Returns a deep copy from self."""
Facundo Batista59c58842007-04-10 12:58:45 +00002307 nc = Context(self.prec, self.rounding, self.traps.copy(),
2308 self.flags.copy(), self._rounding_decision, self.Emin,
2309 self.Emax, self.capitals, self._clamp, self._ignored_flags)
Raymond Hettinger9fce44b2004-08-08 04:03:24 +00002310 return nc
Raymond Hettinger9ec3e3b2004-07-03 13:48:56 +00002311 __copy__ = copy
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00002312
Raymond Hettinger5aa478b2004-07-09 10:02:53 +00002313 def _raise_error(self, condition, explanation = None, *args):
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00002314 """Handles an error
2315
2316 If the flag is in _ignored_flags, returns the default response.
2317 Otherwise, it increments the flag, then, if the corresponding
2318 trap_enabler is set, it reaises the exception. Otherwise, it returns
2319 the default value after incrementing the flag.
2320 """
Raymond Hettinger5aa478b2004-07-09 10:02:53 +00002321 error = _condition_map.get(condition, condition)
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00002322 if error in self._ignored_flags:
Facundo Batista59c58842007-04-10 12:58:45 +00002323 # Don't touch the flag
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00002324 return error().handle(self, *args)
2325
2326 self.flags[error] += 1
Raymond Hettingerbf440692004-07-10 14:14:37 +00002327 if not self.traps[error]:
Facundo Batista59c58842007-04-10 12:58:45 +00002328 # The errors define how to handle themselves.
Raymond Hettinger5aa478b2004-07-09 10:02:53 +00002329 return condition().handle(self, *args)
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00002330
2331 # Errors should only be risked on copies of the context
Facundo Batista59c58842007-04-10 12:58:45 +00002332 # self._ignored_flags = []
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00002333 raise error, explanation
2334
2335 def _ignore_all_flags(self):
2336 """Ignore all flags, if they are raised"""
Raymond Hettingerfed52962004-07-14 15:41:57 +00002337 return self._ignore_flags(*_signals)
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00002338
2339 def _ignore_flags(self, *flags):
2340 """Ignore the flags, if they are raised"""
2341 # Do not mutate-- This way, copies of a context leave the original
2342 # alone.
2343 self._ignored_flags = (self._ignored_flags + list(flags))
2344 return list(flags)
2345
2346 def _regard_flags(self, *flags):
2347 """Stop ignoring the flags, if they are raised"""
2348 if flags and isinstance(flags[0], (tuple,list)):
2349 flags = flags[0]
2350 for flag in flags:
2351 self._ignored_flags.remove(flag)
2352
Raymond Hettinger5aa478b2004-07-09 10:02:53 +00002353 def __hash__(self):
2354 """A Context cannot be hashed."""
2355 # We inherit object.__hash__, so we must deny this explicitly
Facundo Batista59c58842007-04-10 12:58:45 +00002356 raise TypeError("Cannot hash a Context.")
Raymond Hettinger5aa478b2004-07-09 10:02:53 +00002357
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00002358 def Etiny(self):
2359 """Returns Etiny (= Emin - prec + 1)"""
2360 return int(self.Emin - self.prec + 1)
2361
2362 def Etop(self):
Raymond Hettingere0f15812004-07-05 05:36:39 +00002363 """Returns maximum exponent (= Emax - prec + 1)"""
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00002364 return int(self.Emax - self.prec + 1)
2365
2366 def _set_rounding_decision(self, type):
2367 """Sets the rounding decision.
2368
2369 Sets the rounding decision, and returns the current (previous)
2370 rounding decision. Often used like:
2371
Raymond Hettinger9fce44b2004-08-08 04:03:24 +00002372 context = context._shallow_copy()
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00002373 # That so you don't change the calling context
2374 # if an error occurs in the middle (say DivisionImpossible is raised).
2375
2376 rounding = context._set_rounding_decision(NEVER_ROUND)
2377 instance = instance / Decimal(2)
2378 context._set_rounding_decision(rounding)
2379
2380 This will make it not round for that operation.
2381 """
Martin v. Löwiscfe31282006-07-19 17:18:32 +00002382
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00002383 rounding = self._rounding_decision
2384 self._rounding_decision = type
2385 return rounding
2386
2387 def _set_rounding(self, type):
2388 """Sets the rounding type.
2389
2390 Sets the rounding type, and returns the current (previous)
2391 rounding type. Often used like:
2392
2393 context = context.copy()
2394 # so you don't change the calling context
2395 # if an error occurs in the middle.
2396 rounding = context._set_rounding(ROUND_UP)
2397 val = self.__sub__(other, context=context)
2398 context._set_rounding(rounding)
2399
2400 This will make it round up for that operation.
2401 """
2402 rounding = self.rounding
2403 self.rounding= type
2404 return rounding
2405
Raymond Hettingerfed52962004-07-14 15:41:57 +00002406 def create_decimal(self, num='0'):
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00002407 """Creates a new Decimal instance but using self as context."""
2408 d = Decimal(num, context=self)
Raymond Hettingerdab988d2004-10-09 07:10:44 +00002409 return d._fix(self)
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00002410
Facundo Batista59c58842007-04-10 12:58:45 +00002411 # Methods
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00002412 def abs(self, a):
2413 """Returns the absolute value of the operand.
2414
2415 If the operand is negative, the result is the same as using the minus
Facundo Batista59c58842007-04-10 12:58:45 +00002416 operation on the operand. Otherwise, the result is the same as using
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00002417 the plus operation on the operand.
2418
Raymond Hettinger9ec3e3b2004-07-03 13:48:56 +00002419 >>> ExtendedContext.abs(Decimal('2.1'))
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00002420 Decimal("2.1")
Raymond Hettinger9ec3e3b2004-07-03 13:48:56 +00002421 >>> ExtendedContext.abs(Decimal('-100'))
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00002422 Decimal("100")
Raymond Hettinger9ec3e3b2004-07-03 13:48:56 +00002423 >>> ExtendedContext.abs(Decimal('101.5'))
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00002424 Decimal("101.5")
Raymond Hettinger9ec3e3b2004-07-03 13:48:56 +00002425 >>> ExtendedContext.abs(Decimal('-101.5'))
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00002426 Decimal("101.5")
2427 """
2428 return a.__abs__(context=self)
2429
2430 def add(self, a, b):
2431 """Return the sum of the two operands.
2432
Raymond Hettinger9ec3e3b2004-07-03 13:48:56 +00002433 >>> ExtendedContext.add(Decimal('12'), Decimal('7.00'))
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00002434 Decimal("19.00")
Raymond Hettinger9ec3e3b2004-07-03 13:48:56 +00002435 >>> ExtendedContext.add(Decimal('1E+2'), Decimal('1.01E+4'))
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00002436 Decimal("1.02E+4")
2437 """
2438 return a.__add__(b, context=self)
2439
2440 def _apply(self, a):
Raymond Hettingerdab988d2004-10-09 07:10:44 +00002441 return str(a._fix(self))
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00002442
2443 def compare(self, a, b):
2444 """Compares values numerically.
2445
2446 If the signs of the operands differ, a value representing each operand
2447 ('-1' if the operand is less than zero, '0' if the operand is zero or
2448 negative zero, or '1' if the operand is greater than zero) is used in
2449 place of that operand for the comparison instead of the actual
2450 operand.
2451
2452 The comparison is then effected by subtracting the second operand from
2453 the first and then returning a value according to the result of the
2454 subtraction: '-1' if the result is less than zero, '0' if the result is
2455 zero or negative zero, or '1' if the result is greater than zero.
2456
Raymond Hettinger9ec3e3b2004-07-03 13:48:56 +00002457 >>> ExtendedContext.compare(Decimal('2.1'), Decimal('3'))
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00002458 Decimal("-1")
Raymond Hettinger9ec3e3b2004-07-03 13:48:56 +00002459 >>> ExtendedContext.compare(Decimal('2.1'), Decimal('2.1'))
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00002460 Decimal("0")
Raymond Hettinger9ec3e3b2004-07-03 13:48:56 +00002461 >>> ExtendedContext.compare(Decimal('2.1'), Decimal('2.10'))
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00002462 Decimal("0")
Raymond Hettinger9ec3e3b2004-07-03 13:48:56 +00002463 >>> ExtendedContext.compare(Decimal('3'), Decimal('2.1'))
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00002464 Decimal("1")
Raymond Hettinger9ec3e3b2004-07-03 13:48:56 +00002465 >>> ExtendedContext.compare(Decimal('2.1'), Decimal('-3'))
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00002466 Decimal("1")
Raymond Hettinger9ec3e3b2004-07-03 13:48:56 +00002467 >>> ExtendedContext.compare(Decimal('-3'), Decimal('2.1'))
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00002468 Decimal("-1")
2469 """
2470 return a.compare(b, context=self)
2471
2472 def divide(self, a, b):
2473 """Decimal division in a specified context.
2474
Raymond Hettinger9ec3e3b2004-07-03 13:48:56 +00002475 >>> ExtendedContext.divide(Decimal('1'), Decimal('3'))
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00002476 Decimal("0.333333333")
Raymond Hettinger9ec3e3b2004-07-03 13:48:56 +00002477 >>> ExtendedContext.divide(Decimal('2'), Decimal('3'))
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00002478 Decimal("0.666666667")
Raymond Hettinger9ec3e3b2004-07-03 13:48:56 +00002479 >>> ExtendedContext.divide(Decimal('5'), Decimal('2'))
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00002480 Decimal("2.5")
Raymond Hettinger9ec3e3b2004-07-03 13:48:56 +00002481 >>> ExtendedContext.divide(Decimal('1'), Decimal('10'))
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00002482 Decimal("0.1")
Raymond Hettinger9ec3e3b2004-07-03 13:48:56 +00002483 >>> ExtendedContext.divide(Decimal('12'), Decimal('12'))
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00002484 Decimal("1")
Raymond Hettinger9ec3e3b2004-07-03 13:48:56 +00002485 >>> ExtendedContext.divide(Decimal('8.00'), Decimal('2'))
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00002486 Decimal("4.00")
Raymond Hettinger9ec3e3b2004-07-03 13:48:56 +00002487 >>> ExtendedContext.divide(Decimal('2.400'), Decimal('2.0'))
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00002488 Decimal("1.20")
Raymond Hettinger9ec3e3b2004-07-03 13:48:56 +00002489 >>> ExtendedContext.divide(Decimal('1000'), Decimal('100'))
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00002490 Decimal("10")
Raymond Hettinger9ec3e3b2004-07-03 13:48:56 +00002491 >>> ExtendedContext.divide(Decimal('1000'), Decimal('1'))
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00002492 Decimal("1000")
Raymond Hettinger9ec3e3b2004-07-03 13:48:56 +00002493 >>> ExtendedContext.divide(Decimal('2.40E+6'), Decimal('2'))
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00002494 Decimal("1.20E+6")
2495 """
2496 return a.__div__(b, context=self)
2497
2498 def divide_int(self, a, b):
2499 """Divides two numbers and returns the integer part of the result.
2500
Raymond Hettinger9ec3e3b2004-07-03 13:48:56 +00002501 >>> ExtendedContext.divide_int(Decimal('2'), Decimal('3'))
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00002502 Decimal("0")
Raymond Hettinger9ec3e3b2004-07-03 13:48:56 +00002503 >>> ExtendedContext.divide_int(Decimal('10'), Decimal('3'))
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00002504 Decimal("3")
Raymond Hettinger9ec3e3b2004-07-03 13:48:56 +00002505 >>> ExtendedContext.divide_int(Decimal('1'), Decimal('0.3'))
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00002506 Decimal("3")
2507 """
2508 return a.__floordiv__(b, context=self)
2509
2510 def divmod(self, a, b):
2511 return a.__divmod__(b, context=self)
2512
2513 def max(self, a,b):
2514 """max compares two values numerically and returns the maximum.
2515
2516 If either operand is a NaN then the general rules apply.
2517 Otherwise, the operands are compared as as though by the compare
Facundo Batista59c58842007-04-10 12:58:45 +00002518 operation. If they are numerically equal then the left-hand operand
2519 is chosen as the result. Otherwise the maximum (closer to positive
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00002520 infinity) of the two operands is chosen as the result.
2521
Raymond Hettinger9ec3e3b2004-07-03 13:48:56 +00002522 >>> ExtendedContext.max(Decimal('3'), Decimal('2'))
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00002523 Decimal("3")
Raymond Hettinger9ec3e3b2004-07-03 13:48:56 +00002524 >>> ExtendedContext.max(Decimal('-10'), Decimal('3'))
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00002525 Decimal("3")
Raymond Hettinger9ec3e3b2004-07-03 13:48:56 +00002526 >>> ExtendedContext.max(Decimal('1.0'), Decimal('1'))
Raymond Hettingerd6c700a2004-08-17 06:39:37 +00002527 Decimal("1")
2528 >>> ExtendedContext.max(Decimal('7'), Decimal('NaN'))
2529 Decimal("7")
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00002530 """
2531 return a.max(b, context=self)
2532
2533 def min(self, a,b):
2534 """min compares two values numerically and returns the minimum.
2535
2536 If either operand is a NaN then the general rules apply.
2537 Otherwise, the operands are compared as as though by the compare
Facundo Batista59c58842007-04-10 12:58:45 +00002538 operation. If they are numerically equal then the left-hand operand
2539 is chosen as the result. Otherwise the minimum (closer to negative
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00002540 infinity) of the two operands is chosen as the result.
2541
Raymond Hettinger9ec3e3b2004-07-03 13:48:56 +00002542 >>> ExtendedContext.min(Decimal('3'), Decimal('2'))
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00002543 Decimal("2")
Raymond Hettinger9ec3e3b2004-07-03 13:48:56 +00002544 >>> ExtendedContext.min(Decimal('-10'), Decimal('3'))
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00002545 Decimal("-10")
Raymond Hettinger9ec3e3b2004-07-03 13:48:56 +00002546 >>> ExtendedContext.min(Decimal('1.0'), Decimal('1'))
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00002547 Decimal("1.0")
Raymond Hettingerd6c700a2004-08-17 06:39:37 +00002548 >>> ExtendedContext.min(Decimal('7'), Decimal('NaN'))
2549 Decimal("7")
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00002550 """
2551 return a.min(b, context=self)
2552
2553 def minus(self, a):
2554 """Minus corresponds to unary prefix minus in Python.
2555
2556 The operation is evaluated using the same rules as subtract; the
2557 operation minus(a) is calculated as subtract('0', a) where the '0'
2558 has the same exponent as the operand.
2559
Raymond Hettinger9ec3e3b2004-07-03 13:48:56 +00002560 >>> ExtendedContext.minus(Decimal('1.3'))
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00002561 Decimal("-1.3")
Raymond Hettinger9ec3e3b2004-07-03 13:48:56 +00002562 >>> ExtendedContext.minus(Decimal('-1.3'))
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00002563 Decimal("1.3")
2564 """
2565 return a.__neg__(context=self)
2566
2567 def multiply(self, a, b):
2568 """multiply multiplies two operands.
2569
Martin v. Löwiscfe31282006-07-19 17:18:32 +00002570 If either operand is a special value then the general rules apply.
2571 Otherwise, the operands are multiplied together ('long multiplication'),
2572 resulting in a number which may be as long as the sum of the lengths
2573 of the two operands.
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00002574
Raymond Hettinger9ec3e3b2004-07-03 13:48:56 +00002575 >>> ExtendedContext.multiply(Decimal('1.20'), Decimal('3'))
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00002576 Decimal("3.60")
Raymond Hettinger9ec3e3b2004-07-03 13:48:56 +00002577 >>> ExtendedContext.multiply(Decimal('7'), Decimal('3'))
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00002578 Decimal("21")
Raymond Hettinger9ec3e3b2004-07-03 13:48:56 +00002579 >>> ExtendedContext.multiply(Decimal('0.9'), Decimal('0.8'))
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00002580 Decimal("0.72")
Raymond Hettinger9ec3e3b2004-07-03 13:48:56 +00002581 >>> ExtendedContext.multiply(Decimal('0.9'), Decimal('-0'))
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00002582 Decimal("-0.0")
Raymond Hettinger9ec3e3b2004-07-03 13:48:56 +00002583 >>> ExtendedContext.multiply(Decimal('654321'), Decimal('654321'))
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00002584 Decimal("4.28135971E+11")
2585 """
2586 return a.__mul__(b, context=self)
2587
2588 def normalize(self, a):
Raymond Hettingere0f15812004-07-05 05:36:39 +00002589 """normalize reduces an operand to its simplest form.
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00002590
2591 Essentially a plus operation with all trailing zeros removed from the
2592 result.
2593
Raymond Hettinger9ec3e3b2004-07-03 13:48:56 +00002594 >>> ExtendedContext.normalize(Decimal('2.1'))
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00002595 Decimal("2.1")
Raymond Hettinger9ec3e3b2004-07-03 13:48:56 +00002596 >>> ExtendedContext.normalize(Decimal('-2.0'))
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00002597 Decimal("-2")
Raymond Hettinger9ec3e3b2004-07-03 13:48:56 +00002598 >>> ExtendedContext.normalize(Decimal('1.200'))
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00002599 Decimal("1.2")
Raymond Hettinger9ec3e3b2004-07-03 13:48:56 +00002600 >>> ExtendedContext.normalize(Decimal('-120'))
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00002601 Decimal("-1.2E+2")
Raymond Hettinger9ec3e3b2004-07-03 13:48:56 +00002602 >>> ExtendedContext.normalize(Decimal('120.00'))
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00002603 Decimal("1.2E+2")
Raymond Hettinger9ec3e3b2004-07-03 13:48:56 +00002604 >>> ExtendedContext.normalize(Decimal('0.00'))
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00002605 Decimal("0")
2606 """
2607 return a.normalize(context=self)
2608
2609 def plus(self, a):
2610 """Plus corresponds to unary prefix plus in Python.
2611
2612 The operation is evaluated using the same rules as add; the
2613 operation plus(a) is calculated as add('0', a) where the '0'
2614 has the same exponent as the operand.
2615
Raymond Hettinger9ec3e3b2004-07-03 13:48:56 +00002616 >>> ExtendedContext.plus(Decimal('1.3'))
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00002617 Decimal("1.3")
Raymond Hettinger9ec3e3b2004-07-03 13:48:56 +00002618 >>> ExtendedContext.plus(Decimal('-1.3'))
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00002619 Decimal("-1.3")
2620 """
2621 return a.__pos__(context=self)
2622
2623 def power(self, a, b, modulo=None):
2624 """Raises a to the power of b, to modulo if given.
2625
2626 The right-hand operand must be a whole number whose integer part (after
2627 any exponent has been applied) has no more than 9 digits and whose
Facundo Batista59c58842007-04-10 12:58:45 +00002628 fractional part (if any) is all zeros before any rounding. The operand
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00002629 may be positive, negative, or zero; if negative, the absolute value of
2630 the power is used, and the left-hand operand is inverted (divided into
2631 1) before use.
2632
2633 If the increased precision needed for the intermediate calculations
Facundo Batista59c58842007-04-10 12:58:45 +00002634 exceeds the capabilities of the implementation then an Invalid
2635 operation condition is raised.
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00002636
2637 If, when raising to a negative power, an underflow occurs during the
2638 division into 1, the operation is not halted at that point but
2639 continues.
2640
Raymond Hettinger9ec3e3b2004-07-03 13:48:56 +00002641 >>> ExtendedContext.power(Decimal('2'), Decimal('3'))
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00002642 Decimal("8")
Raymond Hettinger9ec3e3b2004-07-03 13:48:56 +00002643 >>> ExtendedContext.power(Decimal('2'), Decimal('-3'))
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00002644 Decimal("0.125")
Raymond Hettinger9ec3e3b2004-07-03 13:48:56 +00002645 >>> ExtendedContext.power(Decimal('1.7'), Decimal('8'))
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00002646 Decimal("69.7575744")
Raymond Hettinger9ec3e3b2004-07-03 13:48:56 +00002647 >>> ExtendedContext.power(Decimal('Infinity'), Decimal('-2'))
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00002648 Decimal("0")
Raymond Hettinger9ec3e3b2004-07-03 13:48:56 +00002649 >>> ExtendedContext.power(Decimal('Infinity'), Decimal('-1'))
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00002650 Decimal("0")
Raymond Hettinger9ec3e3b2004-07-03 13:48:56 +00002651 >>> ExtendedContext.power(Decimal('Infinity'), Decimal('0'))
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00002652 Decimal("1")
Raymond Hettinger9ec3e3b2004-07-03 13:48:56 +00002653 >>> ExtendedContext.power(Decimal('Infinity'), Decimal('1'))
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00002654 Decimal("Infinity")
Raymond Hettinger9ec3e3b2004-07-03 13:48:56 +00002655 >>> ExtendedContext.power(Decimal('Infinity'), Decimal('2'))
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00002656 Decimal("Infinity")
Raymond Hettinger9ec3e3b2004-07-03 13:48:56 +00002657 >>> ExtendedContext.power(Decimal('-Infinity'), Decimal('-2'))
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00002658 Decimal("0")
Raymond Hettinger9ec3e3b2004-07-03 13:48:56 +00002659 >>> ExtendedContext.power(Decimal('-Infinity'), Decimal('-1'))
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00002660 Decimal("-0")
Raymond Hettinger9ec3e3b2004-07-03 13:48:56 +00002661 >>> ExtendedContext.power(Decimal('-Infinity'), Decimal('0'))
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00002662 Decimal("1")
Raymond Hettinger9ec3e3b2004-07-03 13:48:56 +00002663 >>> ExtendedContext.power(Decimal('-Infinity'), Decimal('1'))
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00002664 Decimal("-Infinity")
Raymond Hettinger9ec3e3b2004-07-03 13:48:56 +00002665 >>> ExtendedContext.power(Decimal('-Infinity'), Decimal('2'))
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00002666 Decimal("Infinity")
Raymond Hettinger9ec3e3b2004-07-03 13:48:56 +00002667 >>> ExtendedContext.power(Decimal('0'), Decimal('0'))
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00002668 Decimal("NaN")
2669 """
2670 return a.__pow__(b, modulo, context=self)
2671
2672 def quantize(self, a, b):
Facundo Batista59c58842007-04-10 12:58:45 +00002673 """Returns a value equal to 'a' (rounded), having the exponent of 'b'.
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00002674
2675 The coefficient of the result is derived from that of the left-hand
Facundo Batista59c58842007-04-10 12:58:45 +00002676 operand. It may be rounded using the current rounding setting (if the
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00002677 exponent is being increased), multiplied by a positive power of ten (if
2678 the exponent is being decreased), or is unchanged (if the exponent is
2679 already equal to that of the right-hand operand).
2680
2681 Unlike other operations, if the length of the coefficient after the
2682 quantize operation would be greater than precision then an Invalid
Facundo Batista59c58842007-04-10 12:58:45 +00002683 operation condition is raised. This guarantees that, unless there is
2684 an error condition, the exponent of the result of a quantize is always
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00002685 equal to that of the right-hand operand.
2686
2687 Also unlike other operations, quantize will never raise Underflow, even
2688 if the result is subnormal and inexact.
2689
Raymond Hettinger9ec3e3b2004-07-03 13:48:56 +00002690 >>> ExtendedContext.quantize(Decimal('2.17'), Decimal('0.001'))
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00002691 Decimal("2.170")
Raymond Hettinger9ec3e3b2004-07-03 13:48:56 +00002692 >>> ExtendedContext.quantize(Decimal('2.17'), Decimal('0.01'))
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00002693 Decimal("2.17")
Raymond Hettinger9ec3e3b2004-07-03 13:48:56 +00002694 >>> ExtendedContext.quantize(Decimal('2.17'), Decimal('0.1'))
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00002695 Decimal("2.2")
Raymond Hettinger9ec3e3b2004-07-03 13:48:56 +00002696 >>> ExtendedContext.quantize(Decimal('2.17'), Decimal('1e+0'))
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00002697 Decimal("2")
Raymond Hettinger9ec3e3b2004-07-03 13:48:56 +00002698 >>> ExtendedContext.quantize(Decimal('2.17'), Decimal('1e+1'))
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00002699 Decimal("0E+1")
Raymond Hettinger9ec3e3b2004-07-03 13:48:56 +00002700 >>> ExtendedContext.quantize(Decimal('-Inf'), Decimal('Infinity'))
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00002701 Decimal("-Infinity")
Raymond Hettinger9ec3e3b2004-07-03 13:48:56 +00002702 >>> ExtendedContext.quantize(Decimal('2'), Decimal('Infinity'))
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00002703 Decimal("NaN")
Raymond Hettinger9ec3e3b2004-07-03 13:48:56 +00002704 >>> ExtendedContext.quantize(Decimal('-0.1'), Decimal('1'))
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00002705 Decimal("-0")
Raymond Hettinger9ec3e3b2004-07-03 13:48:56 +00002706 >>> ExtendedContext.quantize(Decimal('-0'), Decimal('1e+5'))
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00002707 Decimal("-0E+5")
Raymond Hettinger9ec3e3b2004-07-03 13:48:56 +00002708 >>> ExtendedContext.quantize(Decimal('+35236450.6'), Decimal('1e-2'))
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00002709 Decimal("NaN")
Raymond Hettinger9ec3e3b2004-07-03 13:48:56 +00002710 >>> ExtendedContext.quantize(Decimal('-35236450.6'), Decimal('1e-2'))
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00002711 Decimal("NaN")
Raymond Hettinger9ec3e3b2004-07-03 13:48:56 +00002712 >>> ExtendedContext.quantize(Decimal('217'), Decimal('1e-1'))
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00002713 Decimal("217.0")
Raymond Hettinger9ec3e3b2004-07-03 13:48:56 +00002714 >>> ExtendedContext.quantize(Decimal('217'), Decimal('1e-0'))
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00002715 Decimal("217")
Raymond Hettinger9ec3e3b2004-07-03 13:48:56 +00002716 >>> ExtendedContext.quantize(Decimal('217'), Decimal('1e+1'))
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00002717 Decimal("2.2E+2")
Raymond Hettinger9ec3e3b2004-07-03 13:48:56 +00002718 >>> ExtendedContext.quantize(Decimal('217'), Decimal('1e+2'))
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00002719 Decimal("2E+2")
2720 """
2721 return a.quantize(b, context=self)
2722
2723 def remainder(self, a, b):
2724 """Returns the remainder from integer division.
2725
2726 The result is the residue of the dividend after the operation of
Facundo Batista59c58842007-04-10 12:58:45 +00002727 calculating integer division as described for divide-integer, rounded
2728 to precision digits if necessary. The sign of the result, if
2729 non-zero, is the same as that of the original dividend.
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00002730
2731 This operation will fail under the same conditions as integer division
2732 (that is, if integer division on the same two operands would fail, the
2733 remainder cannot be calculated).
2734
Raymond Hettinger9ec3e3b2004-07-03 13:48:56 +00002735 >>> ExtendedContext.remainder(Decimal('2.1'), Decimal('3'))
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00002736 Decimal("2.1")
Raymond Hettinger9ec3e3b2004-07-03 13:48:56 +00002737 >>> ExtendedContext.remainder(Decimal('10'), Decimal('3'))
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00002738 Decimal("1")
Raymond Hettinger9ec3e3b2004-07-03 13:48:56 +00002739 >>> ExtendedContext.remainder(Decimal('-10'), Decimal('3'))
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00002740 Decimal("-1")
Raymond Hettinger9ec3e3b2004-07-03 13:48:56 +00002741 >>> ExtendedContext.remainder(Decimal('10.2'), Decimal('1'))
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00002742 Decimal("0.2")
Raymond Hettinger9ec3e3b2004-07-03 13:48:56 +00002743 >>> ExtendedContext.remainder(Decimal('10'), Decimal('0.3'))
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00002744 Decimal("0.1")
Raymond Hettinger9ec3e3b2004-07-03 13:48:56 +00002745 >>> ExtendedContext.remainder(Decimal('3.6'), Decimal('1.3'))
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00002746 Decimal("1.0")
2747 """
2748 return a.__mod__(b, context=self)
2749
2750 def remainder_near(self, a, b):
2751 """Returns to be "a - b * n", where n is the integer nearest the exact
2752 value of "x / b" (if two integers are equally near then the even one
Facundo Batista59c58842007-04-10 12:58:45 +00002753 is chosen). If the result is equal to 0 then its sign will be the
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00002754 sign of a.
2755
2756 This operation will fail under the same conditions as integer division
2757 (that is, if integer division on the same two operands would fail, the
2758 remainder cannot be calculated).
2759
Raymond Hettinger9ec3e3b2004-07-03 13:48:56 +00002760 >>> ExtendedContext.remainder_near(Decimal('2.1'), Decimal('3'))
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00002761 Decimal("-0.9")
Raymond Hettinger9ec3e3b2004-07-03 13:48:56 +00002762 >>> ExtendedContext.remainder_near(Decimal('10'), Decimal('6'))
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00002763 Decimal("-2")
Raymond Hettinger9ec3e3b2004-07-03 13:48:56 +00002764 >>> ExtendedContext.remainder_near(Decimal('10'), Decimal('3'))
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00002765 Decimal("1")
Raymond Hettinger9ec3e3b2004-07-03 13:48:56 +00002766 >>> ExtendedContext.remainder_near(Decimal('-10'), Decimal('3'))
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00002767 Decimal("-1")
Raymond Hettinger9ec3e3b2004-07-03 13:48:56 +00002768 >>> ExtendedContext.remainder_near(Decimal('10.2'), Decimal('1'))
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00002769 Decimal("0.2")
Raymond Hettinger9ec3e3b2004-07-03 13:48:56 +00002770 >>> ExtendedContext.remainder_near(Decimal('10'), Decimal('0.3'))
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00002771 Decimal("0.1")
Raymond Hettinger9ec3e3b2004-07-03 13:48:56 +00002772 >>> ExtendedContext.remainder_near(Decimal('3.6'), Decimal('1.3'))
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00002773 Decimal("-0.3")
2774 """
2775 return a.remainder_near(b, context=self)
2776
2777 def same_quantum(self, a, b):
2778 """Returns True if the two operands have the same exponent.
2779
2780 The result is never affected by either the sign or the coefficient of
2781 either operand.
2782
Raymond Hettinger9ec3e3b2004-07-03 13:48:56 +00002783 >>> ExtendedContext.same_quantum(Decimal('2.17'), Decimal('0.001'))
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00002784 False
Raymond Hettinger9ec3e3b2004-07-03 13:48:56 +00002785 >>> ExtendedContext.same_quantum(Decimal('2.17'), Decimal('0.01'))
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00002786 True
Raymond Hettinger9ec3e3b2004-07-03 13:48:56 +00002787 >>> ExtendedContext.same_quantum(Decimal('2.17'), Decimal('1'))
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00002788 False
Raymond Hettinger9ec3e3b2004-07-03 13:48:56 +00002789 >>> ExtendedContext.same_quantum(Decimal('Inf'), Decimal('-Inf'))
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00002790 True
2791 """
2792 return a.same_quantum(b)
2793
2794 def sqrt(self, a):
Facundo Batista59c58842007-04-10 12:58:45 +00002795 """Square root of a non-negative number to context precision.
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00002796
2797 If the result must be inexact, it is rounded using the round-half-even
2798 algorithm.
2799
Raymond Hettinger9ec3e3b2004-07-03 13:48:56 +00002800 >>> ExtendedContext.sqrt(Decimal('0'))
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00002801 Decimal("0")
Raymond Hettinger9ec3e3b2004-07-03 13:48:56 +00002802 >>> ExtendedContext.sqrt(Decimal('-0'))
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00002803 Decimal("-0")
Raymond Hettinger9ec3e3b2004-07-03 13:48:56 +00002804 >>> ExtendedContext.sqrt(Decimal('0.39'))
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00002805 Decimal("0.624499800")
Raymond Hettinger9ec3e3b2004-07-03 13:48:56 +00002806 >>> ExtendedContext.sqrt(Decimal('100'))
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00002807 Decimal("10")
Raymond Hettinger9ec3e3b2004-07-03 13:48:56 +00002808 >>> ExtendedContext.sqrt(Decimal('1'))
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00002809 Decimal("1")
Raymond Hettinger9ec3e3b2004-07-03 13:48:56 +00002810 >>> ExtendedContext.sqrt(Decimal('1.0'))
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00002811 Decimal("1.0")
Raymond Hettinger9ec3e3b2004-07-03 13:48:56 +00002812 >>> ExtendedContext.sqrt(Decimal('1.00'))
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00002813 Decimal("1.0")
Raymond Hettinger9ec3e3b2004-07-03 13:48:56 +00002814 >>> ExtendedContext.sqrt(Decimal('7'))
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00002815 Decimal("2.64575131")
Raymond Hettinger9ec3e3b2004-07-03 13:48:56 +00002816 >>> ExtendedContext.sqrt(Decimal('10'))
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00002817 Decimal("3.16227766")
Raymond Hettinger9ec3e3b2004-07-03 13:48:56 +00002818 >>> ExtendedContext.prec
Raymond Hettinger6ea48452004-07-03 12:26:21 +00002819 9
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00002820 """
2821 return a.sqrt(context=self)
2822
2823 def subtract(self, a, b):
Georg Brandlf33d01d2005-08-22 19:35:18 +00002824 """Return the difference between the two operands.
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00002825
Raymond Hettinger9ec3e3b2004-07-03 13:48:56 +00002826 >>> ExtendedContext.subtract(Decimal('1.3'), Decimal('1.07'))
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00002827 Decimal("0.23")
Raymond Hettinger9ec3e3b2004-07-03 13:48:56 +00002828 >>> ExtendedContext.subtract(Decimal('1.3'), Decimal('1.30'))
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00002829 Decimal("0.00")
Raymond Hettinger9ec3e3b2004-07-03 13:48:56 +00002830 >>> ExtendedContext.subtract(Decimal('1.3'), Decimal('2.07'))
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00002831 Decimal("-0.77")
2832 """
2833 return a.__sub__(b, context=self)
2834
2835 def to_eng_string(self, a):
2836 """Converts a number to a string, using scientific notation.
2837
2838 The operation is not affected by the context.
2839 """
2840 return a.to_eng_string(context=self)
2841
2842 def to_sci_string(self, a):
2843 """Converts a number to a string, using scientific notation.
2844
2845 The operation is not affected by the context.
2846 """
2847 return a.__str__(context=self)
2848
2849 def to_integral(self, a):
2850 """Rounds to an integer.
2851
2852 When the operand has a negative exponent, the result is the same
2853 as using the quantize() operation using the given operand as the
2854 left-hand-operand, 1E+0 as the right-hand-operand, and the precision
2855 of the operand as the precision setting, except that no flags will
Facundo Batista59c58842007-04-10 12:58:45 +00002856 be set. The rounding mode is taken from the context.
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00002857
Raymond Hettinger9ec3e3b2004-07-03 13:48:56 +00002858 >>> ExtendedContext.to_integral(Decimal('2.1'))
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00002859 Decimal("2")
Raymond Hettinger9ec3e3b2004-07-03 13:48:56 +00002860 >>> ExtendedContext.to_integral(Decimal('100'))
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00002861 Decimal("100")
Raymond Hettinger9ec3e3b2004-07-03 13:48:56 +00002862 >>> ExtendedContext.to_integral(Decimal('100.0'))
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00002863 Decimal("100")
Raymond Hettinger9ec3e3b2004-07-03 13:48:56 +00002864 >>> ExtendedContext.to_integral(Decimal('101.5'))
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00002865 Decimal("102")
Raymond Hettinger9ec3e3b2004-07-03 13:48:56 +00002866 >>> ExtendedContext.to_integral(Decimal('-101.5'))
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00002867 Decimal("-102")
Raymond Hettinger9ec3e3b2004-07-03 13:48:56 +00002868 >>> ExtendedContext.to_integral(Decimal('10E+5'))
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00002869 Decimal("1.0E+6")
Raymond Hettinger9ec3e3b2004-07-03 13:48:56 +00002870 >>> ExtendedContext.to_integral(Decimal('7.89E+77'))
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00002871 Decimal("7.89E+77")
Raymond Hettinger9ec3e3b2004-07-03 13:48:56 +00002872 >>> ExtendedContext.to_integral(Decimal('-Inf'))
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00002873 Decimal("-Infinity")
2874 """
2875 return a.to_integral(context=self)
2876
2877class _WorkRep(object):
2878 __slots__ = ('sign','int','exp')
Raymond Hettinger17931de2004-10-27 06:21:46 +00002879 # sign: 0 or 1
Raymond Hettinger636a6b12004-09-19 01:54:09 +00002880 # int: int or long
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00002881 # exp: None, int, or string
2882
2883 def __init__(self, value=None):
2884 if value is None:
2885 self.sign = None
Raymond Hettinger636a6b12004-09-19 01:54:09 +00002886 self.int = 0
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00002887 self.exp = None
Raymond Hettinger17931de2004-10-27 06:21:46 +00002888 elif isinstance(value, Decimal):
2889 self.sign = value._sign
Raymond Hettinger636a6b12004-09-19 01:54:09 +00002890 cum = 0
Raymond Hettinger17931de2004-10-27 06:21:46 +00002891 for digit in value._int:
Raymond Hettinger636a6b12004-09-19 01:54:09 +00002892 cum = cum * 10 + digit
2893 self.int = cum
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00002894 self.exp = value._exp
Raymond Hettinger17931de2004-10-27 06:21:46 +00002895 else:
2896 # assert isinstance(value, tuple)
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00002897 self.sign = value[0]
2898 self.int = value[1]
2899 self.exp = value[2]
2900
2901 def __repr__(self):
2902 return "(%r, %r, %r)" % (self.sign, self.int, self.exp)
2903
2904 __str__ = __repr__
2905
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00002906
2907
2908def _normalize(op1, op2, shouldround = 0, prec = 0):
2909 """Normalizes op1, op2 to have the same exp and length of coefficient.
2910
2911 Done during addition.
2912 """
2913 # Yes, the exponent is a long, but the difference between exponents
2914 # must be an int-- otherwise you'd get a big memory problem.
2915 numdigits = int(op1.exp - op2.exp)
2916 if numdigits < 0:
2917 numdigits = -numdigits
2918 tmp = op2
2919 other = op1
2920 else:
2921 tmp = op1
2922 other = op2
2923
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00002924
Raymond Hettinger636a6b12004-09-19 01:54:09 +00002925 if shouldround and numdigits > prec + 1:
2926 # Big difference in exponents - check the adjusted exponents
2927 tmp_len = len(str(tmp.int))
2928 other_len = len(str(other.int))
2929 if numdigits > (other_len + prec + 1 - tmp_len):
2930 # If the difference in adjusted exps is > prec+1, we know
Facundo Batista59c58842007-04-10 12:58:45 +00002931 # other is insignificant, so might as well put a 1 after the
2932 # precision (since this is only for addition). Also stops
2933 # use of massive longs.
Martin v. Löwiscfe31282006-07-19 17:18:32 +00002934
Raymond Hettinger636a6b12004-09-19 01:54:09 +00002935 extend = prec + 2 - tmp_len
2936 if extend <= 0:
2937 extend = 1
2938 tmp.int *= 10 ** extend
2939 tmp.exp -= extend
2940 other.int = 1
2941 other.exp = tmp.exp
2942 return op1, op2
2943
2944 tmp.int *= 10 ** numdigits
2945 tmp.exp -= numdigits
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00002946 return op1, op2
2947
2948def _adjust_coefficients(op1, op2):
Raymond Hettinger636a6b12004-09-19 01:54:09 +00002949 """Adjust op1, op2 so that op2.int * 10 > op1.int >= op2.int.
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00002950
2951 Returns the adjusted op1, op2 as well as the change in op1.exp-op2.exp.
2952
2953 Used on _WorkRep instances during division.
2954 """
2955 adjust = 0
Facundo Batista59c58842007-04-10 12:58:45 +00002956 # If op1 is smaller, make it larger
Raymond Hettinger636a6b12004-09-19 01:54:09 +00002957 while op2.int > op1.int:
2958 op1.int *= 10
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00002959 op1.exp -= 1
Raymond Hettinger636a6b12004-09-19 01:54:09 +00002960 adjust += 1
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00002961
Facundo Batista59c58842007-04-10 12:58:45 +00002962 # If op2 is too small, make it larger
Raymond Hettinger636a6b12004-09-19 01:54:09 +00002963 while op1.int >= (10 * op2.int):
2964 op2.int *= 10
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00002965 op2.exp -= 1
2966 adjust -= 1
Raymond Hettinger636a6b12004-09-19 01:54:09 +00002967
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00002968 return op1, op2, adjust
2969
Facundo Batista59c58842007-04-10 12:58:45 +00002970##### Helper Functions ####################################################
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00002971
Raymond Hettinger636a6b12004-09-19 01:54:09 +00002972def _convert_other(other):
2973 """Convert other to Decimal.
2974
2975 Verifies that it's ok to use in an implicit construction.
2976 """
2977 if isinstance(other, Decimal):
2978 return other
2979 if isinstance(other, (int, long)):
2980 return Decimal(other)
Raymond Hettinger267b8682005-03-27 10:47:39 +00002981 return NotImplemented
Raymond Hettinger636a6b12004-09-19 01:54:09 +00002982
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00002983_infinity_map = {
2984 'inf' : 1,
2985 'infinity' : 1,
2986 '+inf' : 1,
2987 '+infinity' : 1,
2988 '-inf' : -1,
2989 '-infinity' : -1
2990}
2991
Raymond Hettinger0ea241e2004-07-04 13:53:24 +00002992def _isinfinity(num):
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00002993 """Determines whether a string or float is infinity.
2994
Raymond Hettinger0ea241e2004-07-04 13:53:24 +00002995 +1 for negative infinity; 0 for finite ; +1 for positive infinity
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00002996 """
2997 num = str(num).lower()
2998 return _infinity_map.get(num, 0)
2999
Raymond Hettinger0ea241e2004-07-04 13:53:24 +00003000def _isnan(num):
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00003001 """Determines whether a string or float is NaN
3002
3003 (1, sign, diagnostic info as string) => NaN
3004 (2, sign, diagnostic info as string) => sNaN
3005 0 => not a NaN
3006 """
3007 num = str(num).lower()
3008 if not num:
3009 return 0
3010
Facundo Batista59c58842007-04-10 12:58:45 +00003011 # Get the sign, get rid of trailing [+-]
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00003012 sign = 0
3013 if num[0] == '+':
3014 num = num[1:]
Facundo Batista59c58842007-04-10 12:58:45 +00003015 elif num[0] == '-': # elif avoids '+-nan'
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00003016 num = num[1:]
3017 sign = 1
3018
3019 if num.startswith('nan'):
Facundo Batista59c58842007-04-10 12:58:45 +00003020 if len(num) > 3 and not num[3:].isdigit(): # diagnostic info
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00003021 return 0
3022 return (1, sign, num[3:].lstrip('0'))
3023 if num.startswith('snan'):
3024 if len(num) > 4 and not num[4:].isdigit():
3025 return 0
3026 return (2, sign, num[4:].lstrip('0'))
3027 return 0
3028
3029
Facundo Batista59c58842007-04-10 12:58:45 +00003030##### Setup Specific Contexts ############################################
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00003031
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00003032# The default context prototype used by Context()
Raymond Hettingerfed52962004-07-14 15:41:57 +00003033# Is mutable, so that new contexts can have different default values
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00003034
3035DefaultContext = Context(
Raymond Hettinger6ea48452004-07-03 12:26:21 +00003036 prec=28, rounding=ROUND_HALF_EVEN,
Raymond Hettingerbf440692004-07-10 14:14:37 +00003037 traps=[DivisionByZero, Overflow, InvalidOperation],
3038 flags=[],
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00003039 _rounding_decision=ALWAYS_ROUND,
Raymond Hettinger99148e72004-07-14 19:56:56 +00003040 Emax=999999999,
3041 Emin=-999999999,
Raymond Hettingere0f15812004-07-05 05:36:39 +00003042 capitals=1
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00003043)
3044
3045# Pre-made alternate contexts offered by the specification
3046# Don't change these; the user should be able to select these
3047# contexts and be able to reproduce results from other implementations
3048# of the spec.
3049
Raymond Hettinger9ec3e3b2004-07-03 13:48:56 +00003050BasicContext = Context(
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00003051 prec=9, rounding=ROUND_HALF_UP,
Raymond Hettingerbf440692004-07-10 14:14:37 +00003052 traps=[DivisionByZero, Overflow, InvalidOperation, Clamped, Underflow],
3053 flags=[],
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00003054)
3055
Raymond Hettinger9ec3e3b2004-07-03 13:48:56 +00003056ExtendedContext = Context(
Raymond Hettinger6ea48452004-07-03 12:26:21 +00003057 prec=9, rounding=ROUND_HALF_EVEN,
Raymond Hettingerbf440692004-07-10 14:14:37 +00003058 traps=[],
3059 flags=[],
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00003060)
3061
3062
Facundo Batista59c58842007-04-10 12:58:45 +00003063##### Useful Constants (internal use only) ################################
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00003064
Facundo Batista59c58842007-04-10 12:58:45 +00003065# Reusable defaults
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00003066Inf = Decimal('Inf')
3067negInf = Decimal('-Inf')
3068
Facundo Batista59c58842007-04-10 12:58:45 +00003069# Infsign[sign] is infinity w/ that sign
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00003070Infsign = (Inf, negInf)
3071
3072NaN = Decimal('NaN')
3073
3074
Facundo Batista59c58842007-04-10 12:58:45 +00003075##### crud for parsing strings #############################################
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00003076import re
3077
3078# There's an optional sign at the start, and an optional exponent
3079# at the end. The exponent has an optional sign and at least one
3080# digit. In between, must have either at least one digit followed
3081# by an optional fraction, or a decimal point followed by at least
3082# one digit. Yuck.
3083
3084_parser = re.compile(r"""
3085# \s*
3086 (?P<sign>[-+])?
3087 (
3088 (?P<int>\d+) (\. (?P<frac>\d*))?
3089 |
3090 \. (?P<onlyfrac>\d+)
3091 )
3092 ([eE](?P<exp>[-+]? \d+))?
3093# \s*
3094 $
Facundo Batista59c58842007-04-10 12:58:45 +00003095""", re.VERBOSE).match # Uncomment the \s* to allow leading or trailing spaces.
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00003096
3097del re
3098
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00003099def _string2exact(s):
Facundo Batista59c58842007-04-10 12:58:45 +00003100 """Return sign, n, p s.t.
3101
3102 Float string value == -1**sign * n * 10**p exactly
3103 """
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00003104 m = _parser(s)
3105 if m is None:
3106 raise ValueError("invalid literal for Decimal: %r" % s)
3107
3108 if m.group('sign') == "-":
3109 sign = 1
3110 else:
3111 sign = 0
3112
3113 exp = m.group('exp')
3114 if exp is None:
3115 exp = 0
3116 else:
3117 exp = int(exp)
3118
3119 intpart = m.group('int')
3120 if intpart is None:
3121 intpart = ""
3122 fracpart = m.group('onlyfrac')
3123 else:
3124 fracpart = m.group('frac')
3125 if fracpart is None:
3126 fracpart = ""
3127
3128 exp -= len(fracpart)
3129
3130 mantissa = intpart + fracpart
3131 tmp = map(int, mantissa)
3132 backup = tmp
3133 while tmp and tmp[0] == 0:
3134 del tmp[0]
3135
3136 # It's a zero
3137 if not tmp:
3138 if backup:
3139 return (sign, tuple(backup), exp)
3140 return (sign, (0,), exp)
3141 mantissa = tuple(tmp)
3142
3143 return (sign, mantissa, exp)
3144
3145
3146if __name__ == '__main__':
3147 import doctest, sys
3148 doctest.testmod(sys.modules[__name__])