blob: fb11e8f3e4fee5c08be6794ef6dc54ba3340eaf7 [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
32The purpose of the module is to support arithmetic using familiar
33"schoolhouse" rules and to avoid the some of tricky representation
34issues 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
Raymond Hettinger0ea241e2004-07-04 13:53:24 +0000134 'setcontext', 'getcontext'
Raymond Hettinger7c85fa42004-07-01 11:01:35 +0000135]
136
Raymond Hettinger7c85fa42004-07-01 11:01:35 +0000137import copy
Raymond Hettinger7c85fa42004-07-01 11:01:35 +0000138
Raymond Hettinger7c85fa42004-07-01 11:01:35 +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
Raymond Hettinger9ec3e3b2004-07-03 13:48:56 +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
152#Errors
153
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
Raymond Hettinger7c85fa42004-07-01 11:01:35 +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
170 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
182 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
185 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
197 0 * (+-)INF
198 (+-)INF / (+-)INF
199 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:
210 if args[0] == 1: #sNaN, must drop 's' but keep diagnostics
211 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
219 syntax. The result is [0,qNaN].
220 """
221
222 def handle(self, context, *args):
223 return (0, (0,), 'n') #Passed to something which uses a tuple.
224
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 """
237
238 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
248 longer than precision). The result is [0,qNaN].
249 """
250
251 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
259 the dividend is also zero. The result is [0,qNaN].
260 """
261
262 def handle(self, context, tup=None, *args):
263 if tup is not None:
264 return (NaN, NaN) #for 0 %0, 0 // 0
265 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
272 were non-zero), or if an overflow or underflow condition occurs. The
273 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
284 detected during an operation. This can occur if contexts are not checked
285 on creation and either the precision exceeds the capability of the
286 underlying concrete representation or an unknown or unsupported rounding
287 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].
289 """
290
291 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
299 coefficient), or if an overflow or underflow condition occurs. The
300 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
312 Emin, before any rounding). The result in all cases is unchanged.
313
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],
331 where sign is the sign of the intermediate result. For round-down, the
332 result is the largest finite number that can be represented in the
333 current precision, with the sign of the intermediate result. For
334 round-ceiling, the result is the same as for round-down if the sign of
335 the intermediate result is 1, or is [0,inf] otherwise. For round-floor,
336 the result is the same as for round-down if the sign of the intermediate
337 result is 0, or is [1,inf] otherwise. In all cases, Inexact and Rounded
338 will also be raised.
339 """
340
341 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
363 Emin). That is, the result is both inexact and subnormal.
364
365 The result after an underflow will be a subnormal number rounded, if
366 necessary, so that its exponent is not less than Etiny. This may result
367 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,
Raymond Hettinger5aa478b2004-07-09 10:02:53 +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
382##### Context Functions #######################################
383
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
388# mock threading object with threading.local() returning the module namespace.
389
390try:
391 import threading
392except ImportError:
393 # Python was compiled without threads; create a mock object instead
394 import sys
395 class MockThreading:
396 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
Raymond Hettingeref66deb2004-07-14 21:04:27 +0000406 #To fix reloading, force it to create a new context
407 #Old contexts have different exceptions in their dicts, making problems.
408 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
459 del threading, local # Don't contaminate the namespace
Raymond Hettinger7c85fa42004-07-01 11:01:35 +0000460
461
462##### Decimal class ###########################################
463
464class Decimal(object):
465 """Floating point class for decimal arithmetic."""
466
Raymond Hettinger636a6b12004-09-19 01:54:09 +0000467 __slots__ = ('_exp','_int','_sign', '_is_special')
468 # Generally, the value of the Decimal instance is given by
469 # (-1)**_sign * _int * 10**_exp
470 # Special values are signified by _is_special == True
Raymond Hettinger7c85fa42004-07-01 11:01:35 +0000471
Raymond Hettingerdab988d2004-10-09 07:10:44 +0000472 # We're immutable, so use __new__ not __init__
Raymond Hettinger636a6b12004-09-19 01:54:09 +0000473 def __new__(cls, value="0", context=None):
Raymond Hettinger7c85fa42004-07-01 11:01:35 +0000474 """Create a decimal point instance.
475
476 >>> Decimal('3.14') # string input
477 Decimal("3.14")
478 >>> Decimal((0, (3, 1, 4), -2)) # tuple input (sign, digit_tuple, exponent)
479 Decimal("3.14")
480 >>> Decimal(314) # int or long
481 Decimal("314")
482 >>> Decimal(Decimal(314)) # another decimal instance
483 Decimal("314")
484 """
Raymond Hettinger7c85fa42004-07-01 11:01:35 +0000485
Raymond Hettinger636a6b12004-09-19 01:54:09 +0000486 self = object.__new__(cls)
487 self._is_special = False
488
489 # From an internal working value
490 if isinstance(value, _WorkRep):
Raymond Hettinger17931de2004-10-27 06:21:46 +0000491 self._sign = value.sign
Raymond Hettinger636a6b12004-09-19 01:54:09 +0000492 self._int = tuple(map(int, str(value.int)))
493 self._exp = int(value.exp)
494 return self
495
496 # From another decimal
497 if isinstance(value, Decimal):
498 self._exp = value._exp
499 self._sign = value._sign
500 self._int = value._int
501 self._is_special = value._is_special
502 return self
503
504 # From an integer
Raymond Hettinger7c85fa42004-07-01 11:01:35 +0000505 if isinstance(value, (int,long)):
Raymond Hettinger636a6b12004-09-19 01:54:09 +0000506 if value >= 0:
507 self._sign = 0
508 else:
509 self._sign = 1
510 self._exp = 0
511 self._int = tuple(map(int, str(abs(value))))
512 return self
Raymond Hettinger7c85fa42004-07-01 11:01:35 +0000513
514 # tuple/list conversion (possibly from as_tuple())
515 if isinstance(value, (list,tuple)):
516 if len(value) != 3:
517 raise ValueError, 'Invalid arguments'
Raymond Hettingerdbecd932005-02-06 06:57:08 +0000518 if value[0] not in (0,1):
Raymond Hettinger7c85fa42004-07-01 11:01:35 +0000519 raise ValueError, 'Invalid sign'
520 for digit in value[1]:
521 if not isinstance(digit, (int,long)) or digit < 0:
522 raise ValueError, "The second value in the tuple must be composed of non negative integer elements."
523
524 self._sign = value[0]
525 self._int = tuple(value[1])
526 if value[2] in ('F','n','N'):
527 self._exp = value[2]
Raymond Hettinger636a6b12004-09-19 01:54:09 +0000528 self._is_special = True
Raymond Hettinger7c85fa42004-07-01 11:01:35 +0000529 else:
530 self._exp = int(value[2])
Raymond Hettinger636a6b12004-09-19 01:54:09 +0000531 return self
Raymond Hettinger7c85fa42004-07-01 11:01:35 +0000532
Raymond Hettingerbf440692004-07-10 14:14:37 +0000533 if isinstance(value, float):
534 raise TypeError("Cannot convert float to Decimal. " +
535 "First convert the float to a string")
536
Raymond Hettinger636a6b12004-09-19 01:54:09 +0000537 # Other argument types may require the context during interpretation
538 if context is None:
539 context = getcontext()
Raymond Hettinger7c85fa42004-07-01 11:01:35 +0000540
Raymond Hettinger636a6b12004-09-19 01:54:09 +0000541 # From a string
542 # REs insist on real strings, so we can too.
543 if isinstance(value, basestring):
544 if _isinfinity(value):
545 self._exp = 'F'
546 self._int = (0,)
547 self._is_special = True
548 if _isinfinity(value) == 1:
549 self._sign = 0
550 else:
551 self._sign = 1
552 return self
553 if _isnan(value):
554 sig, sign, diag = _isnan(value)
555 self._is_special = True
556 if len(diag) > context.prec: #Diagnostic info too long
557 self._sign, self._int, self._exp = \
558 context._raise_error(ConversionSyntax)
559 return self
560 if sig == 1:
561 self._exp = 'n' #qNaN
562 else: #sig == 2
563 self._exp = 'N' #sNaN
564 self._sign = sign
565 self._int = tuple(map(int, diag)) #Diagnostic info
566 return self
567 try:
568 self._sign, self._int, self._exp = _string2exact(value)
569 except ValueError:
570 self._is_special = True
571 self._sign, self._int, self._exp = context._raise_error(ConversionSyntax)
572 return self
Raymond Hettinger7c85fa42004-07-01 11:01:35 +0000573
Raymond Hettinger636a6b12004-09-19 01:54:09 +0000574 raise TypeError("Cannot convert %r to Decimal" % value)
Raymond Hettinger7c85fa42004-07-01 11:01:35 +0000575
576 def _isnan(self):
577 """Returns whether the number is not actually one.
578
579 0 if a number
580 1 if NaN
581 2 if sNaN
582 """
Raymond Hettinger636a6b12004-09-19 01:54:09 +0000583 if self._is_special:
584 exp = self._exp
585 if exp == 'n':
586 return 1
587 elif exp == 'N':
588 return 2
Raymond Hettinger7c85fa42004-07-01 11:01:35 +0000589 return 0
590
591 def _isinfinity(self):
592 """Returns whether the number is infinite
593
594 0 if finite or not a number
595 1 if +INF
596 -1 if -INF
597 """
598 if self._exp == 'F':
599 if self._sign:
600 return -1
601 return 1
602 return 0
603
604 def _check_nans(self, other = None, context=None):
605 """Returns whether the number is not actually one.
606
607 if self, other are sNaN, signal
608 if self, other are NaN return nan
609 return 0
610
611 Done before operations.
612 """
Raymond Hettinger7c85fa42004-07-01 11:01:35 +0000613
Raymond Hettinger636a6b12004-09-19 01:54:09 +0000614 self_is_nan = self._isnan()
615 if other is None:
616 other_is_nan = False
617 else:
618 other_is_nan = other._isnan()
619
620 if self_is_nan or other_is_nan:
621 if context is None:
622 context = getcontext()
623
624 if self_is_nan == 2:
625 return context._raise_error(InvalidOperation, 'sNaN',
626 1, self)
627 if other_is_nan == 2:
628 return context._raise_error(InvalidOperation, 'sNaN',
629 1, other)
630 if self_is_nan:
631 return self
632
Raymond Hettinger7c85fa42004-07-01 11:01:35 +0000633 return other
634 return 0
635
Raymond Hettinger7c85fa42004-07-01 11:01:35 +0000636 def __nonzero__(self):
637 """Is the number non-zero?
638
639 0 if self == 0
640 1 if self != 0
641 """
Raymond Hettinger636a6b12004-09-19 01:54:09 +0000642 if self._is_special:
Raymond Hettinger7c85fa42004-07-01 11:01:35 +0000643 return 1
Raymond Hettinger636a6b12004-09-19 01:54:09 +0000644 return sum(self._int) != 0
Raymond Hettinger7c85fa42004-07-01 11:01:35 +0000645
646 def __cmp__(self, other, context=None):
Raymond Hettinger636a6b12004-09-19 01:54:09 +0000647 other = _convert_other(other)
Raymond Hettinger7c85fa42004-07-01 11:01:35 +0000648
Raymond Hettinger636a6b12004-09-19 01:54:09 +0000649 if self._is_special or other._is_special:
650 ans = self._check_nans(other, context)
651 if ans:
652 return 1 # Comparison involving NaN's always reports self > other
653
654 # INF = INF
655 return cmp(self._isinfinity(), other._isinfinity())
Raymond Hettinger7c85fa42004-07-01 11:01:35 +0000656
657 if not self and not other:
658 return 0 #If both 0, sign comparison isn't certain.
659
660 #If different signs, neg one is less
661 if other._sign < self._sign:
662 return -1
663 if self._sign < other._sign:
664 return 1
665
Raymond Hettinger636a6b12004-09-19 01:54:09 +0000666 self_adjusted = self.adjusted()
667 other_adjusted = other.adjusted()
668 if self_adjusted == other_adjusted and \
Raymond Hettinger7c85fa42004-07-01 11:01:35 +0000669 self._int + (0,)*(self._exp - other._exp) == \
670 other._int + (0,)*(other._exp - self._exp):
671 return 0 #equal, except in precision. ([0]*(-x) = [])
Raymond Hettinger636a6b12004-09-19 01:54:09 +0000672 elif self_adjusted > other_adjusted and self._int[0] != 0:
Raymond Hettinger7c85fa42004-07-01 11:01:35 +0000673 return (-1)**self._sign
Raymond Hettinger636a6b12004-09-19 01:54:09 +0000674 elif self_adjusted < other_adjusted and other._int[0] != 0:
Raymond Hettinger7c85fa42004-07-01 11:01:35 +0000675 return -((-1)**self._sign)
676
Raymond Hettinger636a6b12004-09-19 01:54:09 +0000677 # Need to round, so make sure we have a valid context
678 if context is None:
679 context = getcontext()
680
Raymond Hettinger9fce44b2004-08-08 04:03:24 +0000681 context = context._shallow_copy()
Raymond Hettinger7c85fa42004-07-01 11:01:35 +0000682 rounding = context._set_rounding(ROUND_UP) #round away from 0
683
684 flags = context._ignore_all_flags()
685 res = self.__sub__(other, context=context)
686
687 context._regard_flags(*flags)
688
689 context.rounding = rounding
690
691 if not res:
692 return 0
693 elif res._sign:
694 return -1
695 return 1
696
Raymond Hettinger0aeac102004-07-05 22:53:03 +0000697 def __eq__(self, other):
698 if not isinstance(other, (Decimal, int, long)):
699 return False
700 return self.__cmp__(other) == 0
701
702 def __ne__(self, other):
703 if not isinstance(other, (Decimal, int, long)):
704 return True
705 return self.__cmp__(other) != 0
706
Raymond Hettinger7c85fa42004-07-01 11:01:35 +0000707 def compare(self, other, context=None):
708 """Compares one to another.
709
710 -1 => a < b
711 0 => a = b
712 1 => a > b
713 NaN => one is NaN
714 Like __cmp__, but returns Decimal instances.
715 """
Raymond Hettinger636a6b12004-09-19 01:54:09 +0000716 other = _convert_other(other)
Raymond Hettinger7c85fa42004-07-01 11:01:35 +0000717
718 #compare(NaN, NaN) = NaN
Raymond Hettinger636a6b12004-09-19 01:54:09 +0000719 if (self._is_special or other and other._is_special):
720 ans = self._check_nans(other, context)
721 if ans:
722 return ans
Raymond Hettinger7c85fa42004-07-01 11:01:35 +0000723
724 return Decimal(self.__cmp__(other, context))
725
726 def __hash__(self):
727 """x.__hash__() <==> hash(x)"""
728 # Decimal integers must hash the same as the ints
729 # Non-integer decimals are normalized and hashed as strings
730 # Normalization assures that hast(100E-1) == hash(10)
Raymond Hettingerbea3f6f2005-03-15 04:59:17 +0000731 if self._is_special:
732 if self._isnan():
733 raise TypeError('Cannot hash a NaN value.')
734 return hash(str(self))
Raymond Hettinger7c85fa42004-07-01 11:01:35 +0000735 i = int(self)
736 if self == Decimal(i):
737 return hash(i)
738 assert self.__nonzero__() # '-0' handled by integer case
739 return hash(str(self.normalize()))
740
741 def as_tuple(self):
742 """Represents the number as a triple tuple.
743
744 To show the internals exactly as they are.
745 """
746 return (self._sign, self._int, self._exp)
747
748 def __repr__(self):
749 """Represents the number as an instance of Decimal."""
750 # Invariant: eval(repr(d)) == d
751 return 'Decimal("%s")' % str(self)
752
753 def __str__(self, eng = 0, context=None):
754 """Return string representation of the number in scientific notation.
755
756 Captures all of the information in the underlying representation.
757 """
758
759 if self._isnan():
760 minus = '-'*self._sign
761 if self._int == (0,):
762 info = ''
763 else:
764 info = ''.join(map(str, self._int))
765 if self._isnan() == 2:
766 return minus + 'sNaN' + info
767 return minus + 'NaN' + info
768 if self._isinfinity():
769 minus = '-'*self._sign
770 return minus + 'Infinity'
771
772 if context is None:
773 context = getcontext()
774
775 tmp = map(str, self._int)
776 numdigits = len(self._int)
777 leftdigits = self._exp + numdigits
778 if eng and not self: #self = 0eX wants 0[.0[0]]eY, not [[0]0]0eY
779 if self._exp < 0 and self._exp >= -6: #short, no need for e/E
780 s = '-'*self._sign + '0.' + '0'*(abs(self._exp))
781 return s
782 #exp is closest mult. of 3 >= self._exp
783 exp = ((self._exp - 1)// 3 + 1) * 3
784 if exp != self._exp:
785 s = '0.'+'0'*(exp - self._exp)
786 else:
787 s = '0'
788 if exp != 0:
789 if context.capitals:
790 s += 'E'
791 else:
792 s += 'e'
793 if exp > 0:
794 s += '+' #0.0e+3, not 0.0e3
795 s += str(exp)
796 s = '-'*self._sign + s
797 return s
798 if eng:
799 dotplace = (leftdigits-1)%3+1
800 adjexp = leftdigits -1 - (leftdigits-1)%3
801 else:
802 adjexp = leftdigits-1
803 dotplace = 1
804 if self._exp == 0:
805 pass
806 elif self._exp < 0 and adjexp >= 0:
807 tmp.insert(leftdigits, '.')
808 elif self._exp < 0 and adjexp >= -6:
809 tmp[0:0] = ['0'] * int(-leftdigits)
810 tmp.insert(0, '0.')
811 else:
812 if numdigits > dotplace:
813 tmp.insert(dotplace, '.')
814 elif numdigits < dotplace:
815 tmp.extend(['0']*(dotplace-numdigits))
816 if adjexp:
817 if not context.capitals:
818 tmp.append('e')
819 else:
820 tmp.append('E')
821 if adjexp > 0:
822 tmp.append('+')
823 tmp.append(str(adjexp))
824 if eng:
825 while tmp[0:1] == ['0']:
826 tmp[0:1] = []
827 if len(tmp) == 0 or tmp[0] == '.' or tmp[0].lower() == 'e':
828 tmp[0:0] = ['0']
829 if self._sign:
830 tmp.insert(0, '-')
831
832 return ''.join(tmp)
833
834 def to_eng_string(self, context=None):
835 """Convert to engineering-type string.
836
837 Engineering notation has an exponent which is a multiple of 3, so there
838 are up to 3 digits left of the decimal place.
839
840 Same rules for when in exponential and when as a value as in __str__.
841 """
Raymond Hettinger7c85fa42004-07-01 11:01:35 +0000842 return self.__str__(eng=1, context=context)
843
844 def __neg__(self, context=None):
845 """Returns a copy with the sign switched.
846
847 Rounds, if it has reason.
848 """
Raymond Hettinger636a6b12004-09-19 01:54:09 +0000849 if self._is_special:
850 ans = self._check_nans(context=context)
851 if ans:
852 return ans
Raymond Hettinger7c85fa42004-07-01 11:01:35 +0000853
854 if not self:
855 # -Decimal('0') is Decimal('0'), not Decimal('-0')
856 sign = 0
857 elif self._sign:
858 sign = 0
859 else:
860 sign = 1
Raymond Hettinger636a6b12004-09-19 01:54:09 +0000861
862 if context is None:
863 context = getcontext()
Raymond Hettinger7c85fa42004-07-01 11:01:35 +0000864 if context._rounding_decision == ALWAYS_ROUND:
Raymond Hettingerdab988d2004-10-09 07:10:44 +0000865 return Decimal((sign, self._int, self._exp))._fix(context)
Raymond Hettinger7c85fa42004-07-01 11:01:35 +0000866 return Decimal( (sign, self._int, self._exp))
867
868 def __pos__(self, context=None):
869 """Returns a copy, unless it is a sNaN.
870
871 Rounds the number (if more then precision digits)
872 """
Raymond Hettinger636a6b12004-09-19 01:54:09 +0000873 if self._is_special:
874 ans = self._check_nans(context=context)
875 if ans:
876 return ans
Raymond Hettinger7c85fa42004-07-01 11:01:35 +0000877
878 sign = self._sign
879 if not self:
880 # + (-0) = 0
881 sign = 0
882
Raymond Hettinger636a6b12004-09-19 01:54:09 +0000883 if context is None:
884 context = getcontext()
885
Raymond Hettinger7c85fa42004-07-01 11:01:35 +0000886 if context._rounding_decision == ALWAYS_ROUND:
Raymond Hettingerdab988d2004-10-09 07:10:44 +0000887 ans = self._fix(context)
Raymond Hettinger7c85fa42004-07-01 11:01:35 +0000888 else:
889 ans = Decimal(self)
890 ans._sign = sign
891 return ans
892
893 def __abs__(self, round=1, context=None):
894 """Returns the absolute value of self.
895
896 If the second argument is 0, do not round.
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 round:
Raymond Hettinger636a6b12004-09-19 01:54:09 +0000904 if context is None:
905 context = getcontext()
Raymond Hettinger9fce44b2004-08-08 04:03:24 +0000906 context = context._shallow_copy()
Raymond Hettinger7c85fa42004-07-01 11:01:35 +0000907 context._set_rounding_decision(NEVER_ROUND)
908
909 if self._sign:
910 ans = self.__neg__(context=context)
911 else:
912 ans = self.__pos__(context=context)
913
914 return ans
915
916 def __add__(self, other, context=None):
917 """Returns self + other.
918
919 -INF + INF (or the reverse) cause InvalidOperation errors.
920 """
Raymond Hettinger636a6b12004-09-19 01:54:09 +0000921 other = _convert_other(other)
922
Raymond Hettinger7c85fa42004-07-01 11:01:35 +0000923 if context is None:
924 context = getcontext()
Raymond Hettinger7c85fa42004-07-01 11:01:35 +0000925
Raymond Hettinger636a6b12004-09-19 01:54:09 +0000926 if self._is_special or other._is_special:
927 ans = self._check_nans(other, context)
928 if ans:
929 return ans
Raymond Hettinger7c85fa42004-07-01 11:01:35 +0000930
Raymond Hettinger636a6b12004-09-19 01:54:09 +0000931 if self._isinfinity():
932 #If both INF, same sign => same as both, opposite => error.
933 if self._sign != other._sign and other._isinfinity():
934 return context._raise_error(InvalidOperation, '-INF + INF')
935 return Decimal(self)
936 if other._isinfinity():
937 return Decimal(other) #Can't both be infinity here
Raymond Hettinger7c85fa42004-07-01 11:01:35 +0000938
939 shouldround = context._rounding_decision == ALWAYS_ROUND
940
941 exp = min(self._exp, other._exp)
942 negativezero = 0
943 if context.rounding == ROUND_FLOOR and self._sign != other._sign:
944 #If the answer is 0, the sign should be negative, in this case.
945 negativezero = 1
946
947 if not self and not other:
948 sign = min(self._sign, other._sign)
949 if negativezero:
950 sign = 1
951 return Decimal( (sign, (0,), exp))
952 if not self:
Facundo Batista99b55482004-10-26 23:38:46 +0000953 exp = max(exp, other._exp - context.prec-1)
Raymond Hettinger7c85fa42004-07-01 11:01:35 +0000954 ans = other._rescale(exp, watchexp=0, context=context)
955 if shouldround:
Raymond Hettingerdab988d2004-10-09 07:10:44 +0000956 ans = ans._fix(context)
Raymond Hettinger7c85fa42004-07-01 11:01:35 +0000957 return ans
958 if not other:
Facundo Batista99b55482004-10-26 23:38:46 +0000959 exp = max(exp, self._exp - context.prec-1)
Raymond Hettinger7c85fa42004-07-01 11:01:35 +0000960 ans = self._rescale(exp, watchexp=0, context=context)
961 if shouldround:
Raymond Hettingerdab988d2004-10-09 07:10:44 +0000962 ans = ans._fix(context)
Raymond Hettinger7c85fa42004-07-01 11:01:35 +0000963 return ans
964
965 op1 = _WorkRep(self)
966 op2 = _WorkRep(other)
967 op1, op2 = _normalize(op1, op2, shouldround, context.prec)
968
969 result = _WorkRep()
Raymond Hettinger7c85fa42004-07-01 11:01:35 +0000970 if op1.sign != op2.sign:
Raymond Hettinger7c85fa42004-07-01 11:01:35 +0000971 # Equal and opposite
Raymond Hettinger17931de2004-10-27 06:21:46 +0000972 if op1.int == op2.int:
Raymond Hettinger7c85fa42004-07-01 11:01:35 +0000973 if exp < context.Etiny():
974 exp = context.Etiny()
975 context._raise_error(Clamped)
976 return Decimal((negativezero, (0,), exp))
Raymond Hettinger17931de2004-10-27 06:21:46 +0000977 if op1.int < op2.int:
Raymond Hettinger7c85fa42004-07-01 11:01:35 +0000978 op1, op2 = op2, op1
979 #OK, now abs(op1) > abs(op2)
Raymond Hettinger17931de2004-10-27 06:21:46 +0000980 if op1.sign == 1:
981 result.sign = 1
Raymond Hettinger7c85fa42004-07-01 11:01:35 +0000982 op1.sign, op2.sign = op2.sign, op1.sign
983 else:
Raymond Hettinger17931de2004-10-27 06:21:46 +0000984 result.sign = 0
Raymond Hettinger7c85fa42004-07-01 11:01:35 +0000985 #So we know the sign, and op1 > 0.
Raymond Hettinger17931de2004-10-27 06:21:46 +0000986 elif op1.sign == 1:
Raymond Hettinger7c85fa42004-07-01 11:01:35 +0000987 result.sign = 1
Raymond Hettinger17931de2004-10-27 06:21:46 +0000988 op1.sign, op2.sign = (0, 0)
989 else:
990 result.sign = 0
Raymond Hettinger7c85fa42004-07-01 11:01:35 +0000991 #Now, op1 > abs(op2) > 0
992
Raymond Hettinger17931de2004-10-27 06:21:46 +0000993 if op2.sign == 0:
Raymond Hettinger636a6b12004-09-19 01:54:09 +0000994 result.int = op1.int + op2.int
Raymond Hettinger7c85fa42004-07-01 11:01:35 +0000995 else:
Raymond Hettinger636a6b12004-09-19 01:54:09 +0000996 result.int = op1.int - op2.int
Raymond Hettinger7c85fa42004-07-01 11:01:35 +0000997
998 result.exp = op1.exp
999 ans = Decimal(result)
1000 if shouldround:
Raymond Hettingerdab988d2004-10-09 07:10:44 +00001001 ans = ans._fix(context)
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00001002 return ans
1003
1004 __radd__ = __add__
1005
1006 def __sub__(self, other, context=None):
1007 """Return self + (-other)"""
Raymond Hettinger636a6b12004-09-19 01:54:09 +00001008 other = _convert_other(other)
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00001009
Raymond Hettinger636a6b12004-09-19 01:54:09 +00001010 if self._is_special or other._is_special:
1011 ans = self._check_nans(other, context=context)
1012 if ans:
1013 return ans
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00001014
1015 # -Decimal(0) = Decimal(0), which we don't want since
1016 # (-0 - 0 = -0 + (-0) = -0, but -0 + 0 = 0.)
1017 # so we change the sign directly to a copy
1018 tmp = Decimal(other)
1019 tmp._sign = 1-tmp._sign
1020
1021 return self.__add__(tmp, context=context)
1022
1023 def __rsub__(self, other, context=None):
1024 """Return other + (-self)"""
Raymond Hettinger636a6b12004-09-19 01:54:09 +00001025 other = _convert_other(other)
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00001026
1027 tmp = Decimal(self)
1028 tmp._sign = 1 - tmp._sign
1029 return other.__add__(tmp, context=context)
1030
1031 def _increment(self, round=1, context=None):
1032 """Special case of add, adding 1eExponent
1033
1034 Since it is common, (rounding, for example) this adds
1035 (sign)*one E self._exp to the number more efficiently than add.
1036
1037 For example:
1038 Decimal('5.624e10')._increment() == Decimal('5.625e10')
1039 """
Raymond Hettinger636a6b12004-09-19 01:54:09 +00001040 if self._is_special:
1041 ans = self._check_nans(context=context)
1042 if ans:
1043 return ans
1044
1045 return Decimal(self) # Must be infinite, and incrementing makes no difference
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00001046
1047 L = list(self._int)
1048 L[-1] += 1
1049 spot = len(L)-1
1050 while L[spot] == 10:
1051 L[spot] = 0
1052 if spot == 0:
1053 L[0:0] = [1]
1054 break
1055 L[spot-1] += 1
1056 spot -= 1
1057 ans = Decimal((self._sign, L, self._exp))
1058
Raymond Hettinger636a6b12004-09-19 01:54:09 +00001059 if context is None:
1060 context = getcontext()
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00001061 if round and context._rounding_decision == ALWAYS_ROUND:
Raymond Hettingerdab988d2004-10-09 07:10:44 +00001062 ans = ans._fix(context)
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00001063 return ans
1064
1065 def __mul__(self, other, context=None):
1066 """Return self * other.
1067
1068 (+-) INF * 0 (or its reverse) raise InvalidOperation.
1069 """
Raymond Hettinger636a6b12004-09-19 01:54:09 +00001070 other = _convert_other(other)
1071
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00001072 if context is None:
1073 context = getcontext()
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00001074
Raymond Hettingerd87ac8f2004-07-09 10:52:54 +00001075 resultsign = self._sign ^ other._sign
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00001076
Raymond Hettinger636a6b12004-09-19 01:54:09 +00001077 if self._is_special or other._is_special:
1078 ans = self._check_nans(other, context)
1079 if ans:
1080 return ans
1081
1082 if self._isinfinity():
1083 if not other:
1084 return context._raise_error(InvalidOperation, '(+-)INF * 0')
1085 return Infsign[resultsign]
1086
1087 if other._isinfinity():
1088 if not self:
1089 return context._raise_error(InvalidOperation, '0 * (+-)INF')
1090 return Infsign[resultsign]
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00001091
1092 resultexp = self._exp + other._exp
1093 shouldround = context._rounding_decision == ALWAYS_ROUND
1094
1095 # Special case for multiplying by zero
1096 if not self or not other:
1097 ans = Decimal((resultsign, (0,), resultexp))
1098 if shouldround:
1099 #Fixing in case the exponent is out of bounds
Raymond Hettingerdab988d2004-10-09 07:10:44 +00001100 ans = ans._fix(context)
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00001101 return ans
1102
1103 # Special case for multiplying by power of 10
1104 if self._int == (1,):
1105 ans = Decimal((resultsign, other._int, resultexp))
1106 if shouldround:
Raymond Hettingerdab988d2004-10-09 07:10:44 +00001107 ans = ans._fix(context)
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00001108 return ans
1109 if other._int == (1,):
1110 ans = Decimal((resultsign, self._int, resultexp))
1111 if shouldround:
Raymond Hettingerdab988d2004-10-09 07:10:44 +00001112 ans = ans._fix(context)
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00001113 return ans
1114
Raymond Hettinger636a6b12004-09-19 01:54:09 +00001115 op1 = _WorkRep(self)
1116 op2 = _WorkRep(other)
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00001117
Raymond Hettinger636a6b12004-09-19 01:54:09 +00001118 ans = Decimal( (resultsign, map(int, str(op1.int * op2.int)), resultexp))
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00001119 if shouldround:
Raymond Hettingerdab988d2004-10-09 07:10:44 +00001120 ans = ans._fix(context)
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00001121
1122 return ans
1123 __rmul__ = __mul__
1124
1125 def __div__(self, other, context=None):
1126 """Return self / other."""
1127 return self._divide(other, context=context)
1128 __truediv__ = __div__
1129
1130 def _divide(self, other, divmod = 0, context=None):
1131 """Return a / b, to context.prec precision.
1132
1133 divmod:
1134 0 => true division
1135 1 => (a //b, a%b)
1136 2 => a //b
1137 3 => a%b
1138
1139 Actually, if divmod is 2 or 3 a tuple is returned, but errors for
1140 computing the other value are not raised.
1141 """
Raymond Hettinger636a6b12004-09-19 01:54:09 +00001142 other = _convert_other(other)
1143
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00001144 if context is None:
1145 context = getcontext()
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00001146
Raymond Hettingerd87ac8f2004-07-09 10:52:54 +00001147 sign = self._sign ^ other._sign
Raymond Hettinger636a6b12004-09-19 01:54:09 +00001148
1149 if self._is_special or other._is_special:
1150 ans = self._check_nans(other, context)
1151 if ans:
1152 if divmod:
1153 return (ans, ans)
1154 return ans
1155
1156 if self._isinfinity() and other._isinfinity():
1157 if divmod:
1158 return (context._raise_error(InvalidOperation,
1159 '(+-)INF // (+-)INF'),
1160 context._raise_error(InvalidOperation,
1161 '(+-)INF % (+-)INF'))
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00001162 return context._raise_error(InvalidOperation, '(+-)INF/(+-)INF')
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00001163
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00001164 if self._isinfinity():
1165 if divmod == 1:
1166 return (Infsign[sign],
1167 context._raise_error(InvalidOperation, 'INF % x'))
1168 elif divmod == 2:
1169 return (Infsign[sign], NaN)
1170 elif divmod == 3:
1171 return (Infsign[sign],
1172 context._raise_error(InvalidOperation, 'INF % x'))
Raymond Hettinger636a6b12004-09-19 01:54:09 +00001173 return Infsign[sign]
1174
1175 if other._isinfinity():
1176 if divmod:
1177 return (Decimal((sign, (0,), 0)), Decimal(self))
1178 context._raise_error(Clamped, 'Division by infinity')
1179 return Decimal((sign, (0,), context.Etiny()))
1180
1181 # Special cases for zeroes
1182 if not self and not other:
1183 if divmod:
1184 return context._raise_error(DivisionUndefined, '0 / 0', 1)
1185 return context._raise_error(DivisionUndefined, '0 / 0')
1186
1187 if not self:
1188 if divmod:
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00001189 otherside = Decimal(self)
1190 otherside._exp = min(self._exp, other._exp)
1191 return (Decimal((sign, (0,), 0)), otherside)
Raymond Hettinger636a6b12004-09-19 01:54:09 +00001192 exp = self._exp - other._exp
1193 if exp < context.Etiny():
1194 exp = context.Etiny()
1195 context._raise_error(Clamped, '0e-x / y')
1196 if exp > context.Emax:
1197 exp = context.Emax
1198 context._raise_error(Clamped, '0e+x / y')
1199 return Decimal( (sign, (0,), exp) )
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00001200
Raymond Hettinger636a6b12004-09-19 01:54:09 +00001201 if not other:
1202 if divmod:
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00001203 return context._raise_error(DivisionByZero, 'divmod(x,0)',
1204 sign, 1)
Raymond Hettinger636a6b12004-09-19 01:54:09 +00001205 return context._raise_error(DivisionByZero, 'x / 0', sign)
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00001206
Raymond Hettinger636a6b12004-09-19 01:54:09 +00001207 #OK, so neither = 0, INF or NaN
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00001208
1209 shouldround = context._rounding_decision == ALWAYS_ROUND
1210
1211 #If we're dividing into ints, and self < other, stop.
1212 #self.__abs__(0) does not round.
1213 if divmod and (self.__abs__(0, context) < other.__abs__(0, context)):
1214
1215 if divmod == 1 or divmod == 3:
1216 exp = min(self._exp, other._exp)
1217 ans2 = self._rescale(exp, context=context, watchexp=0)
1218 if shouldround:
Raymond Hettingerdab988d2004-10-09 07:10:44 +00001219 ans2 = ans2._fix(context)
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00001220 return (Decimal( (sign, (0,), 0) ),
1221 ans2)
1222
1223 elif divmod == 2:
1224 #Don't round the mod part, if we don't need it.
1225 return (Decimal( (sign, (0,), 0) ), Decimal(self))
1226
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00001227 op1 = _WorkRep(self)
1228 op2 = _WorkRep(other)
1229 op1, op2, adjust = _adjust_coefficients(op1, op2)
Raymond Hettinger636a6b12004-09-19 01:54:09 +00001230 res = _WorkRep( (sign, 0, (op1.exp - op2.exp)) )
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00001231 if divmod and res.exp > context.prec + 1:
1232 return context._raise_error(DivisionImpossible)
1233
Raymond Hettinger636a6b12004-09-19 01:54:09 +00001234 prec_limit = 10 ** context.prec
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00001235 while 1:
Raymond Hettinger636a6b12004-09-19 01:54:09 +00001236 while op2.int <= op1.int:
1237 res.int += 1
1238 op1.int -= op2.int
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00001239 if res.exp == 0 and divmod:
Raymond Hettinger636a6b12004-09-19 01:54:09 +00001240 if res.int >= prec_limit and shouldround:
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00001241 return context._raise_error(DivisionImpossible)
1242 otherside = Decimal(op1)
1243 frozen = context._ignore_all_flags()
1244
1245 exp = min(self._exp, other._exp)
Raymond Hettinger17931de2004-10-27 06:21:46 +00001246 otherside = otherside._rescale(exp, context=context, watchexp=0)
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00001247 context._regard_flags(*frozen)
1248 if shouldround:
Raymond Hettingerdab988d2004-10-09 07:10:44 +00001249 otherside = otherside._fix(context)
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00001250 return (Decimal(res), otherside)
1251
Raymond Hettinger636a6b12004-09-19 01:54:09 +00001252 if op1.int == 0 and adjust >= 0 and not divmod:
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00001253 break
Raymond Hettinger636a6b12004-09-19 01:54:09 +00001254 if res.int >= prec_limit and shouldround:
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00001255 if divmod:
1256 return context._raise_error(DivisionImpossible)
1257 shouldround=1
1258 # Really, the answer is a bit higher, so adding a one to
1259 # the end will make sure the rounding is right.
Raymond Hettinger636a6b12004-09-19 01:54:09 +00001260 if op1.int != 0:
1261 res.int *= 10
1262 res.int += 1
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00001263 res.exp -= 1
1264
1265 break
Raymond Hettinger636a6b12004-09-19 01:54:09 +00001266 res.int *= 10
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00001267 res.exp -= 1
1268 adjust += 1
Raymond Hettinger636a6b12004-09-19 01:54:09 +00001269 op1.int *= 10
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00001270 op1.exp -= 1
1271
Raymond Hettinger636a6b12004-09-19 01:54:09 +00001272 if res.exp == 0 and divmod and op2.int > op1.int:
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00001273 #Solves an error in precision. Same as a previous block.
1274
Raymond Hettinger636a6b12004-09-19 01:54:09 +00001275 if res.int >= prec_limit and shouldround:
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00001276 return context._raise_error(DivisionImpossible)
1277 otherside = Decimal(op1)
1278 frozen = context._ignore_all_flags()
1279
1280 exp = min(self._exp, other._exp)
1281 otherside = otherside._rescale(exp, context=context)
1282
1283 context._regard_flags(*frozen)
1284
1285 return (Decimal(res), otherside)
1286
1287 ans = Decimal(res)
1288 if shouldround:
Raymond Hettingerdab988d2004-10-09 07:10:44 +00001289 ans = ans._fix(context)
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00001290 return ans
1291
1292 def __rdiv__(self, other, context=None):
1293 """Swaps self/other and returns __div__."""
Raymond Hettinger636a6b12004-09-19 01:54:09 +00001294 other = _convert_other(other)
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00001295 return other.__div__(self, context=context)
1296 __rtruediv__ = __rdiv__
1297
1298 def __divmod__(self, other, context=None):
1299 """
1300 (self // other, self % other)
1301 """
1302 return self._divide(other, 1, context)
1303
1304 def __rdivmod__(self, other, context=None):
1305 """Swaps self/other and returns __divmod__."""
Raymond Hettinger636a6b12004-09-19 01:54:09 +00001306 other = _convert_other(other)
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00001307 return other.__divmod__(self, context=context)
1308
1309 def __mod__(self, other, context=None):
1310 """
1311 self % other
1312 """
Raymond Hettinger636a6b12004-09-19 01:54:09 +00001313 other = _convert_other(other)
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00001314
Raymond Hettinger636a6b12004-09-19 01:54:09 +00001315 if self._is_special or other._is_special:
1316 ans = self._check_nans(other, context)
1317 if ans:
1318 return ans
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00001319
1320 if self and not other:
1321 return context._raise_error(InvalidOperation, 'x % 0')
1322
1323 return self._divide(other, 3, context)[1]
1324
1325 def __rmod__(self, other, context=None):
1326 """Swaps self/other and returns __mod__."""
Raymond Hettinger636a6b12004-09-19 01:54:09 +00001327 other = _convert_other(other)
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00001328 return other.__mod__(self, context=context)
1329
1330 def remainder_near(self, other, context=None):
1331 """
1332 Remainder nearest to 0- abs(remainder-near) <= other/2
1333 """
Raymond Hettinger636a6b12004-09-19 01:54:09 +00001334 other = _convert_other(other)
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00001335
Raymond Hettinger636a6b12004-09-19 01:54:09 +00001336 if self._is_special or other._is_special:
1337 ans = self._check_nans(other, context)
1338 if ans:
1339 return ans
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00001340 if self and not other:
1341 return context._raise_error(InvalidOperation, 'x % 0')
1342
Raymond Hettinger636a6b12004-09-19 01:54:09 +00001343 if context is None:
1344 context = getcontext()
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00001345 # If DivisionImpossible causes an error, do not leave Rounded/Inexact
1346 # ignored in the calling function.
Raymond Hettinger9fce44b2004-08-08 04:03:24 +00001347 context = context._shallow_copy()
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00001348 flags = context._ignore_flags(Rounded, Inexact)
1349 #keep DivisionImpossible flags
1350 (side, r) = self.__divmod__(other, context=context)
1351
1352 if r._isnan():
1353 context._regard_flags(*flags)
1354 return r
1355
Raymond Hettinger9fce44b2004-08-08 04:03:24 +00001356 context = context._shallow_copy()
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00001357 rounding = context._set_rounding_decision(NEVER_ROUND)
1358
1359 if other._sign:
1360 comparison = other.__div__(Decimal(-2), context=context)
1361 else:
1362 comparison = other.__div__(Decimal(2), context=context)
1363
1364 context._set_rounding_decision(rounding)
1365 context._regard_flags(*flags)
1366
1367 s1, s2 = r._sign, comparison._sign
1368 r._sign, comparison._sign = 0, 0
1369
1370 if r < comparison:
1371 r._sign, comparison._sign = s1, s2
1372 #Get flags now
1373 self.__divmod__(other, context=context)
Raymond Hettingerdab988d2004-10-09 07:10:44 +00001374 return r._fix(context)
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00001375 r._sign, comparison._sign = s1, s2
1376
1377 rounding = context._set_rounding_decision(NEVER_ROUND)
1378
1379 (side, r) = self.__divmod__(other, context=context)
1380 context._set_rounding_decision(rounding)
1381 if r._isnan():
1382 return r
1383
1384 decrease = not side._iseven()
1385 rounding = context._set_rounding_decision(NEVER_ROUND)
1386 side = side.__abs__(context=context)
1387 context._set_rounding_decision(rounding)
1388
1389 s1, s2 = r._sign, comparison._sign
1390 r._sign, comparison._sign = 0, 0
1391 if r > comparison or decrease and r == comparison:
1392 r._sign, comparison._sign = s1, s2
1393 context.prec += 1
1394 if len(side.__add__(Decimal(1), context=context)._int) >= context.prec:
1395 context.prec -= 1
1396 return context._raise_error(DivisionImpossible)[1]
1397 context.prec -= 1
1398 if self._sign == other._sign:
1399 r = r.__sub__(other, context=context)
1400 else:
1401 r = r.__add__(other, context=context)
1402 else:
1403 r._sign, comparison._sign = s1, s2
1404
Raymond Hettingerdab988d2004-10-09 07:10:44 +00001405 return r._fix(context)
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00001406
1407 def __floordiv__(self, other, context=None):
1408 """self // other"""
1409 return self._divide(other, 2, context)[0]
1410
1411 def __rfloordiv__(self, other, context=None):
1412 """Swaps self/other and returns __floordiv__."""
Raymond Hettinger636a6b12004-09-19 01:54:09 +00001413 other = _convert_other(other)
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00001414 return other.__floordiv__(self, context=context)
1415
1416 def __float__(self):
1417 """Float representation."""
1418 return float(str(self))
1419
1420 def __int__(self):
Brett Cannon46b08022005-03-01 03:12:26 +00001421 """Converts self to an int, truncating if necessary."""
Raymond Hettinger636a6b12004-09-19 01:54:09 +00001422 if self._is_special:
1423 if self._isnan():
1424 context = getcontext()
1425 return context._raise_error(InvalidContext)
1426 elif self._isinfinity():
1427 raise OverflowError, "Cannot convert infinity to long"
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00001428 if self._exp >= 0:
Raymond Hettinger605ed022004-11-24 07:28:48 +00001429 s = ''.join(map(str, self._int)) + '0'*self._exp
1430 else:
1431 s = ''.join(map(str, self._int))[:self._exp]
1432 if s == '':
1433 s = '0'
1434 sign = '-'*self._sign
1435 return int(sign + s)
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00001436
1437 def __long__(self):
1438 """Converts to a long.
1439
1440 Equivalent to long(int(self))
1441 """
1442 return long(self.__int__())
1443
Raymond Hettingerdab988d2004-10-09 07:10:44 +00001444 def _fix(self, context):
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00001445 """Round if it is necessary to keep self within prec precision.
1446
1447 Rounds and fixes the exponent. Does not raise on a sNaN.
1448
1449 Arguments:
1450 self - Decimal instance
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00001451 context - context used.
1452 """
Raymond Hettinger636a6b12004-09-19 01:54:09 +00001453 if self._is_special:
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00001454 return self
1455 if context is None:
1456 context = getcontext()
Raymond Hettingerdab988d2004-10-09 07:10:44 +00001457 prec = context.prec
Facundo Batista99b55482004-10-26 23:38:46 +00001458 ans = self._fixexponents(context)
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00001459 if len(ans._int) > prec:
Raymond Hettingerdab988d2004-10-09 07:10:44 +00001460 ans = ans._round(prec, context=context)
Facundo Batista99b55482004-10-26 23:38:46 +00001461 ans = ans._fixexponents(context)
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00001462 return ans
1463
Facundo Batista99b55482004-10-26 23:38:46 +00001464 def _fixexponents(self, context):
Raymond Hettingerdab988d2004-10-09 07:10:44 +00001465 """Fix the exponents and return a copy with the exponent in bounds.
1466 Only call if known to not be a special value.
1467 """
1468 folddown = context._clamp
Raymond Hettinger636a6b12004-09-19 01:54:09 +00001469 Emin = context.Emin
Facundo Batista99b55482004-10-26 23:38:46 +00001470 ans = self
Raymond Hettinger636a6b12004-09-19 01:54:09 +00001471 ans_adjusted = ans.adjusted()
1472 if ans_adjusted < Emin:
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00001473 Etiny = context.Etiny()
1474 if ans._exp < Etiny:
1475 if not ans:
Facundo Batista99b55482004-10-26 23:38:46 +00001476 ans = Decimal(self)
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00001477 ans._exp = Etiny
1478 context._raise_error(Clamped)
1479 return ans
1480 ans = ans._rescale(Etiny, context=context)
1481 #It isn't zero, and exp < Emin => subnormal
1482 context._raise_error(Subnormal)
1483 if context.flags[Inexact]:
1484 context._raise_error(Underflow)
1485 else:
1486 if ans:
1487 #Only raise subnormal if non-zero.
1488 context._raise_error(Subnormal)
Raymond Hettinger636a6b12004-09-19 01:54:09 +00001489 else:
1490 Etop = context.Etop()
1491 if folddown and ans._exp > Etop:
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00001492 context._raise_error(Clamped)
Raymond Hettinger636a6b12004-09-19 01:54:09 +00001493 ans = ans._rescale(Etop, context=context)
1494 else:
1495 Emax = context.Emax
1496 if ans_adjusted > Emax:
1497 if not ans:
Facundo Batista99b55482004-10-26 23:38:46 +00001498 ans = Decimal(self)
Raymond Hettinger636a6b12004-09-19 01:54:09 +00001499 ans._exp = Emax
1500 context._raise_error(Clamped)
1501 return ans
1502 context._raise_error(Inexact)
1503 context._raise_error(Rounded)
1504 return context._raise_error(Overflow, 'above Emax', ans._sign)
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00001505 return ans
1506
1507 def _round(self, prec=None, rounding=None, context=None):
1508 """Returns a rounded version of self.
1509
1510 You can specify the precision or rounding method. Otherwise, the
1511 context determines it.
1512 """
1513
Raymond Hettinger636a6b12004-09-19 01:54:09 +00001514 if self._is_special:
1515 ans = self._check_nans(context=context)
1516 if ans:
1517 return ans
1518
1519 if self._isinfinity():
1520 return Decimal(self)
1521
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00001522 if context is None:
1523 context = getcontext()
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00001524
1525 if rounding is None:
1526 rounding = context.rounding
1527 if prec is None:
1528 prec = context.prec
1529
1530 if not self:
1531 if prec <= 0:
1532 dig = (0,)
1533 exp = len(self._int) - prec + self._exp
1534 else:
1535 dig = (0,) * prec
1536 exp = len(self._int) + self._exp - prec
1537 ans = Decimal((self._sign, dig, exp))
1538 context._raise_error(Rounded)
1539 return ans
1540
1541 if prec == 0:
1542 temp = Decimal(self)
1543 temp._int = (0,)+temp._int
1544 prec = 1
1545 elif prec < 0:
1546 exp = self._exp + len(self._int) - prec - 1
1547 temp = Decimal( (self._sign, (0, 1), exp))
1548 prec = 1
1549 else:
1550 temp = Decimal(self)
1551
1552 numdigits = len(temp._int)
1553 if prec == numdigits:
1554 return temp
1555
1556 # See if we need to extend precision
1557 expdiff = prec - numdigits
1558 if expdiff > 0:
1559 tmp = list(temp._int)
1560 tmp.extend([0] * expdiff)
1561 ans = Decimal( (temp._sign, tmp, temp._exp - expdiff))
1562 return ans
1563
1564 #OK, but maybe all the lost digits are 0.
1565 lostdigits = self._int[expdiff:]
1566 if lostdigits == (0,) * len(lostdigits):
1567 ans = Decimal( (temp._sign, temp._int[:prec], temp._exp - expdiff))
1568 #Rounded, but not Inexact
1569 context._raise_error(Rounded)
1570 return ans
1571
1572 # Okay, let's round and lose data
1573
1574 this_function = getattr(temp, self._pick_rounding_function[rounding])
1575 #Now we've got the rounding function
1576
1577 if prec != context.prec:
Raymond Hettinger9fce44b2004-08-08 04:03:24 +00001578 context = context._shallow_copy()
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00001579 context.prec = prec
1580 ans = this_function(prec, expdiff, context)
1581 context._raise_error(Rounded)
1582 context._raise_error(Inexact, 'Changed in rounding')
1583
1584 return ans
1585
1586 _pick_rounding_function = {}
1587
1588 def _round_down(self, prec, expdiff, context):
1589 """Also known as round-towards-0, truncate."""
1590 return Decimal( (self._sign, self._int[:prec], self._exp - expdiff) )
1591
1592 def _round_half_up(self, prec, expdiff, context, tmp = None):
1593 """Rounds 5 up (away from 0)"""
1594
1595 if tmp is None:
1596 tmp = Decimal( (self._sign,self._int[:prec], self._exp - expdiff))
1597 if self._int[prec] >= 5:
1598 tmp = tmp._increment(round=0, context=context)
1599 if len(tmp._int) > prec:
1600 return Decimal( (tmp._sign, tmp._int[:-1], tmp._exp + 1))
1601 return tmp
1602
1603 def _round_half_even(self, prec, expdiff, context):
1604 """Round 5 to even, rest to nearest."""
1605
1606 tmp = Decimal( (self._sign, self._int[:prec], self._exp - expdiff))
1607 half = (self._int[prec] == 5)
1608 if half:
1609 for digit in self._int[prec+1:]:
1610 if digit != 0:
1611 half = 0
1612 break
1613 if half:
Raymond Hettinger61992ef2004-08-06 23:42:16 +00001614 if self._int[prec-1] & 1 == 0:
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00001615 return tmp
1616 return self._round_half_up(prec, expdiff, context, tmp)
1617
1618 def _round_half_down(self, prec, expdiff, context):
1619 """Round 5 down"""
1620
1621 tmp = Decimal( (self._sign, self._int[:prec], self._exp - expdiff))
1622 half = (self._int[prec] == 5)
1623 if half:
1624 for digit in self._int[prec+1:]:
1625 if digit != 0:
1626 half = 0
1627 break
1628 if half:
1629 return tmp
1630 return self._round_half_up(prec, expdiff, context, tmp)
1631
1632 def _round_up(self, prec, expdiff, context):
1633 """Rounds away from 0."""
1634 tmp = Decimal( (self._sign, self._int[:prec], self._exp - expdiff) )
1635 for digit in self._int[prec:]:
1636 if digit != 0:
1637 tmp = tmp._increment(round=1, context=context)
1638 if len(tmp._int) > prec:
1639 return Decimal( (tmp._sign, tmp._int[:-1], tmp._exp + 1))
1640 else:
1641 return tmp
1642 return tmp
1643
1644 def _round_ceiling(self, prec, expdiff, context):
1645 """Rounds up (not away from 0 if negative.)"""
1646 if self._sign:
1647 return self._round_down(prec, expdiff, context)
1648 else:
1649 return self._round_up(prec, expdiff, context)
1650
1651 def _round_floor(self, prec, expdiff, context):
1652 """Rounds down (not towards 0 if negative)"""
1653 if not self._sign:
1654 return self._round_down(prec, expdiff, context)
1655 else:
1656 return self._round_up(prec, expdiff, context)
1657
1658 def __pow__(self, n, modulo = None, context=None):
1659 """Return self ** n (mod modulo)
1660
1661 If modulo is None (default), don't take it mod modulo.
1662 """
Raymond Hettinger636a6b12004-09-19 01:54:09 +00001663 n = _convert_other(n)
1664
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00001665 if context is None:
1666 context = getcontext()
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00001667
Raymond Hettinger636a6b12004-09-19 01:54:09 +00001668 if self._is_special or n._is_special or n.adjusted() > 8:
1669 #Because the spot << doesn't work with really big exponents
1670 if n._isinfinity() or n.adjusted() > 8:
1671 return context._raise_error(InvalidOperation, 'x ** INF')
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00001672
Raymond Hettinger636a6b12004-09-19 01:54:09 +00001673 ans = self._check_nans(n, context)
1674 if ans:
1675 return ans
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00001676
Raymond Hettinger636a6b12004-09-19 01:54:09 +00001677 if not n._isinteger():
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00001678 return context._raise_error(InvalidOperation, 'x ** (non-integer)')
1679
1680 if not self and not n:
1681 return context._raise_error(InvalidOperation, '0 ** 0')
1682
1683 if not n:
1684 return Decimal(1)
1685
1686 if self == Decimal(1):
1687 return Decimal(1)
1688
1689 sign = self._sign and not n._iseven()
1690 n = int(n)
1691
1692 if self._isinfinity():
1693 if modulo:
1694 return context._raise_error(InvalidOperation, 'INF % x')
1695 if n > 0:
1696 return Infsign[sign]
1697 return Decimal( (sign, (0,), 0) )
1698
1699 #with ludicrously large exponent, just raise an overflow and return inf.
1700 if not modulo and n > 0 and (self._exp + len(self._int) - 1) * n > context.Emax \
1701 and self:
1702
1703 tmp = Decimal('inf')
1704 tmp._sign = sign
1705 context._raise_error(Rounded)
1706 context._raise_error(Inexact)
1707 context._raise_error(Overflow, 'Big power', sign)
1708 return tmp
1709
1710 elength = len(str(abs(n)))
1711 firstprec = context.prec
1712
Raymond Hettinger99148e72004-07-14 19:56:56 +00001713 if not modulo and firstprec + elength + 1 > DefaultContext.Emax:
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00001714 return context._raise_error(Overflow, 'Too much precision.', sign)
1715
1716 mul = Decimal(self)
1717 val = Decimal(1)
Raymond Hettinger9fce44b2004-08-08 04:03:24 +00001718 context = context._shallow_copy()
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00001719 context.prec = firstprec + elength + 1
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00001720 if n < 0:
1721 #n is a long now, not Decimal instance
1722 n = -n
1723 mul = Decimal(1).__div__(mul, context=context)
1724
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00001725 spot = 1
1726 while spot <= n:
1727 spot <<= 1
1728
1729 spot >>= 1
1730 #Spot is the highest power of 2 less than n
1731 while spot:
1732 val = val.__mul__(val, context=context)
1733 if val._isinfinity():
1734 val = Infsign[sign]
1735 break
1736 if spot & n:
1737 val = val.__mul__(mul, context=context)
1738 if modulo is not None:
1739 val = val.__mod__(modulo, context=context)
1740 spot >>= 1
1741 context.prec = firstprec
1742
Raymond Hettinger76e60d62004-10-20 06:58:28 +00001743 if context._rounding_decision == ALWAYS_ROUND:
Raymond Hettingerdab988d2004-10-09 07:10:44 +00001744 return val._fix(context)
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00001745 return val
1746
1747 def __rpow__(self, other, context=None):
1748 """Swaps self/other and returns __pow__."""
Raymond Hettinger636a6b12004-09-19 01:54:09 +00001749 other = _convert_other(other)
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00001750 return other.__pow__(self, context=context)
1751
1752 def normalize(self, context=None):
1753 """Normalize- strip trailing 0s, change anything equal to 0 to 0e0"""
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00001754
Raymond Hettinger636a6b12004-09-19 01:54:09 +00001755 if self._is_special:
1756 ans = self._check_nans(context=context)
1757 if ans:
1758 return ans
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00001759
Raymond Hettingerdab988d2004-10-09 07:10:44 +00001760 dup = self._fix(context)
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00001761 if dup._isinfinity():
1762 return dup
1763
1764 if not dup:
1765 return Decimal( (dup._sign, (0,), 0) )
1766 end = len(dup._int)
1767 exp = dup._exp
1768 while dup._int[end-1] == 0:
1769 exp += 1
1770 end -= 1
1771 return Decimal( (dup._sign, dup._int[:end], exp) )
1772
1773
Raymond Hettingerdab988d2004-10-09 07:10:44 +00001774 def quantize(self, exp, rounding=None, context=None, watchexp=1):
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00001775 """Quantize self so its exponent is the same as that of exp.
1776
1777 Similar to self._rescale(exp._exp) but with error checking.
1778 """
Raymond Hettinger636a6b12004-09-19 01:54:09 +00001779 if self._is_special or exp._is_special:
1780 ans = self._check_nans(exp, context)
1781 if ans:
1782 return ans
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00001783
Raymond Hettinger636a6b12004-09-19 01:54:09 +00001784 if exp._isinfinity() or self._isinfinity():
1785 if exp._isinfinity() and self._isinfinity():
1786 return self #if both are inf, it is OK
1787 if context is None:
1788 context = getcontext()
1789 return context._raise_error(InvalidOperation,
1790 'quantize with one INF')
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00001791 return self._rescale(exp._exp, rounding, context, watchexp)
1792
1793 def same_quantum(self, other):
1794 """Test whether self and other have the same exponent.
1795
1796 same as self._exp == other._exp, except NaN == sNaN
1797 """
Raymond Hettinger636a6b12004-09-19 01:54:09 +00001798 if self._is_special or other._is_special:
1799 if self._isnan() or other._isnan():
1800 return self._isnan() and other._isnan() and True
1801 if self._isinfinity() or other._isinfinity():
1802 return self._isinfinity() and other._isinfinity() and True
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00001803 return self._exp == other._exp
1804
Raymond Hettingerdab988d2004-10-09 07:10:44 +00001805 def _rescale(self, exp, rounding=None, context=None, watchexp=1):
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00001806 """Rescales so that the exponent is exp.
1807
1808 exp = exp to scale to (an integer)
1809 rounding = rounding version
1810 watchexp: if set (default) an error is returned if exp is greater
1811 than Emax or less than Etiny.
1812 """
1813 if context is None:
1814 context = getcontext()
1815
Raymond Hettinger636a6b12004-09-19 01:54:09 +00001816 if self._is_special:
1817 if self._isinfinity():
1818 return context._raise_error(InvalidOperation, 'rescale with an INF')
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00001819
Raymond Hettinger636a6b12004-09-19 01:54:09 +00001820 ans = self._check_nans(context=context)
1821 if ans:
1822 return ans
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00001823
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00001824 if watchexp and (context.Emax < exp or context.Etiny() > exp):
1825 return context._raise_error(InvalidOperation, 'rescale(a, INF)')
1826
1827 if not self:
1828 ans = Decimal(self)
1829 ans._int = (0,)
1830 ans._exp = exp
1831 return ans
1832
1833 diff = self._exp - exp
Raymond Hettingerdab988d2004-10-09 07:10:44 +00001834 digits = len(self._int) + diff
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00001835
1836 if watchexp and digits > context.prec:
1837 return context._raise_error(InvalidOperation, 'Rescale > prec')
1838
1839 tmp = Decimal(self)
Raymond Hettingerdab988d2004-10-09 07:10:44 +00001840 tmp._int = (0,) + tmp._int
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00001841 digits += 1
1842
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00001843 if digits < 0:
1844 tmp._exp = -digits + tmp._exp
1845 tmp._int = (0,1)
1846 digits = 1
1847 tmp = tmp._round(digits, rounding, context=context)
1848
1849 if tmp._int[0] == 0 and len(tmp._int) > 1:
1850 tmp._int = tmp._int[1:]
1851 tmp._exp = exp
1852
Raymond Hettinger636a6b12004-09-19 01:54:09 +00001853 tmp_adjusted = tmp.adjusted()
1854 if tmp and tmp_adjusted < context.Emin:
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00001855 context._raise_error(Subnormal)
Raymond Hettinger636a6b12004-09-19 01:54:09 +00001856 elif tmp and tmp_adjusted > context.Emax:
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00001857 return context._raise_error(InvalidOperation, 'rescale(a, INF)')
1858 return tmp
1859
Raymond Hettingerdab988d2004-10-09 07:10:44 +00001860 def to_integral(self, rounding=None, context=None):
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00001861 """Rounds to the nearest integer, without raising inexact, rounded."""
Raymond Hettinger636a6b12004-09-19 01:54:09 +00001862 if self._is_special:
1863 ans = self._check_nans(context=context)
1864 if ans:
1865 return ans
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00001866 if self._exp >= 0:
1867 return self
Raymond Hettinger636a6b12004-09-19 01:54:09 +00001868 if context is None:
1869 context = getcontext()
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00001870 flags = context._ignore_flags(Rounded, Inexact)
1871 ans = self._rescale(0, rounding, context=context)
1872 context._regard_flags(flags)
1873 return ans
1874
1875 def sqrt(self, context=None):
1876 """Return the square root of self.
1877
1878 Uses a converging algorithm (Xn+1 = 0.5*(Xn + self / Xn))
1879 Should quadratically approach the right answer.
1880 """
Raymond Hettinger636a6b12004-09-19 01:54:09 +00001881 if self._is_special:
1882 ans = self._check_nans(context=context)
1883 if ans:
1884 return ans
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00001885
Raymond Hettinger636a6b12004-09-19 01:54:09 +00001886 if self._isinfinity() and self._sign == 0:
1887 return Decimal(self)
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00001888
1889 if not self:
1890 #exponent = self._exp / 2, using round_down.
1891 #if self._exp < 0:
1892 # exp = (self._exp+1) // 2
1893 #else:
1894 exp = (self._exp) // 2
1895 if self._sign == 1:
1896 #sqrt(-0) = -0
1897 return Decimal( (1, (0,), exp))
1898 else:
1899 return Decimal( (0, (0,), exp))
1900
Raymond Hettinger636a6b12004-09-19 01:54:09 +00001901 if context is None:
1902 context = getcontext()
1903
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00001904 if self._sign == 1:
1905 return context._raise_error(InvalidOperation, 'sqrt(-x), x > 0')
1906
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00001907 tmp = Decimal(self)
1908
Raymond Hettinger4837a222004-09-27 14:23:40 +00001909 expadd = tmp._exp // 2
Raymond Hettinger61992ef2004-08-06 23:42:16 +00001910 if tmp._exp & 1:
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00001911 tmp._int += (0,)
1912 tmp._exp = 0
1913 else:
1914 tmp._exp = 0
1915
Raymond Hettinger9fce44b2004-08-08 04:03:24 +00001916 context = context._shallow_copy()
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00001917 flags = context._ignore_all_flags()
1918 firstprec = context.prec
1919 context.prec = 3
Raymond Hettinger61992ef2004-08-06 23:42:16 +00001920 if tmp.adjusted() & 1 == 0:
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00001921 ans = Decimal( (0, (8,1,9), tmp.adjusted() - 2) )
1922 ans = ans.__add__(tmp.__mul__(Decimal((0, (2,5,9), -2)),
1923 context=context), context=context)
Raymond Hettinger4837a222004-09-27 14:23:40 +00001924 ans._exp -= 1 + tmp.adjusted() // 2
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00001925 else:
1926 ans = Decimal( (0, (2,5,9), tmp._exp + len(tmp._int)- 3) )
1927 ans = ans.__add__(tmp.__mul__(Decimal((0, (8,1,9), -3)),
1928 context=context), context=context)
Raymond Hettinger4837a222004-09-27 14:23:40 +00001929 ans._exp -= 1 + tmp.adjusted() // 2
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00001930
1931 #ans is now a linear approximation.
1932
1933 Emax, Emin = context.Emax, context.Emin
Raymond Hettinger99148e72004-07-14 19:56:56 +00001934 context.Emax, context.Emin = DefaultContext.Emax, DefaultContext.Emin
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00001935
1936 half = Decimal('0.5')
1937
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00001938 maxp = firstprec + 2
1939 rounding = context._set_rounding(ROUND_HALF_EVEN)
1940 while 1:
1941 context.prec = min(2*context.prec - 2, maxp)
1942 ans = half.__mul__(ans.__add__(tmp.__div__(ans, context=context),
1943 context=context), context=context)
1944 if context.prec == maxp:
1945 break
1946
1947 #round to the answer's precision-- the only error can be 1 ulp.
1948 context.prec = firstprec
1949 prevexp = ans.adjusted()
1950 ans = ans._round(context=context)
1951
1952 #Now, check if the other last digits are better.
1953 context.prec = firstprec + 1
1954 # In case we rounded up another digit and we should actually go lower.
1955 if prevexp != ans.adjusted():
1956 ans._int += (0,)
1957 ans._exp -= 1
1958
1959
1960 lower = ans.__sub__(Decimal((0, (5,), ans._exp-1)), context=context)
1961 context._set_rounding(ROUND_UP)
1962 if lower.__mul__(lower, context=context) > (tmp):
1963 ans = ans.__sub__(Decimal((0, (1,), ans._exp)), context=context)
1964
1965 else:
1966 upper = ans.__add__(Decimal((0, (5,), ans._exp-1)),context=context)
1967 context._set_rounding(ROUND_DOWN)
1968 if upper.__mul__(upper, context=context) < tmp:
1969 ans = ans.__add__(Decimal((0, (1,), ans._exp)),context=context)
1970
1971 ans._exp += expadd
1972
1973 context.prec = firstprec
1974 context.rounding = rounding
Raymond Hettingerdab988d2004-10-09 07:10:44 +00001975 ans = ans._fix(context)
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00001976
1977 rounding = context._set_rounding_decision(NEVER_ROUND)
1978 if not ans.__mul__(ans, context=context) == self:
1979 # Only rounded/inexact if here.
1980 context._regard_flags(flags)
1981 context._raise_error(Rounded)
1982 context._raise_error(Inexact)
1983 else:
1984 #Exact answer, so let's set the exponent right.
1985 #if self._exp < 0:
1986 # exp = (self._exp +1)// 2
1987 #else:
1988 exp = self._exp // 2
1989 context.prec += ans._exp - exp
1990 ans = ans._rescale(exp, context=context)
1991 context.prec = firstprec
1992 context._regard_flags(flags)
1993 context.Emax, context.Emin = Emax, Emin
1994
Raymond Hettingerdab988d2004-10-09 07:10:44 +00001995 return ans._fix(context)
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00001996
1997 def max(self, other, context=None):
1998 """Returns the larger value.
1999
2000 like max(self, other) except if one is not a number, returns
2001 NaN (and signals if one is sNaN). Also rounds.
2002 """
Raymond Hettinger636a6b12004-09-19 01:54:09 +00002003 other = _convert_other(other)
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00002004
Raymond Hettinger636a6b12004-09-19 01:54:09 +00002005 if self._is_special or other._is_special:
2006 # if one operand is a quiet NaN and the other is number, then the
2007 # number is always returned
2008 sn = self._isnan()
2009 on = other._isnan()
2010 if sn or on:
2011 if on == 1 and sn != 2:
2012 return self
2013 if sn == 1 and on != 2:
2014 return other
2015 return self._check_nans(other, context)
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00002016
2017 ans = self
Raymond Hettingerd6c700a2004-08-17 06:39:37 +00002018 c = self.__cmp__(other)
2019 if c == 0:
2020 # if both operands are finite and equal in numerical value
2021 # then an ordering is applied:
2022 #
2023 # if the signs differ then max returns the operand with the
2024 # positive sign and min returns the operand with the negative sign
2025 #
2026 # if the signs are the same then the exponent is used to select
2027 # the result.
2028 if self._sign != other._sign:
2029 if self._sign:
2030 ans = other
2031 elif self._exp < other._exp and not self._sign:
2032 ans = other
2033 elif self._exp > other._exp and self._sign:
2034 ans = other
2035 elif c == -1:
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00002036 ans = other
Raymond Hettinger636a6b12004-09-19 01:54:09 +00002037
2038 if context is None:
2039 context = getcontext()
Raymond Hettinger76e60d62004-10-20 06:58:28 +00002040 if context._rounding_decision == ALWAYS_ROUND:
2041 return ans._fix(context)
2042 return ans
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00002043
2044 def min(self, other, context=None):
2045 """Returns the smaller value.
2046
2047 like min(self, other) except if one is not a number, returns
2048 NaN (and signals if one is sNaN). Also rounds.
2049 """
Raymond Hettinger636a6b12004-09-19 01:54:09 +00002050 other = _convert_other(other)
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00002051
Raymond Hettinger636a6b12004-09-19 01:54:09 +00002052 if self._is_special or other._is_special:
2053 # if one operand is a quiet NaN and the other is number, then the
2054 # number is always returned
2055 sn = self._isnan()
2056 on = other._isnan()
2057 if sn or on:
2058 if on == 1 and sn != 2:
2059 return self
2060 if sn == 1 and on != 2:
2061 return other
2062 return self._check_nans(other, context)
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00002063
2064 ans = self
Raymond Hettingerd6c700a2004-08-17 06:39:37 +00002065 c = self.__cmp__(other)
2066 if c == 0:
2067 # if both operands are finite and equal in numerical value
2068 # then an ordering is applied:
2069 #
2070 # if the signs differ then max returns the operand with the
2071 # positive sign and min returns the operand with the negative sign
2072 #
2073 # if the signs are the same then the exponent is used to select
2074 # the result.
2075 if self._sign != other._sign:
2076 if other._sign:
2077 ans = other
2078 elif self._exp > other._exp and not self._sign:
2079 ans = other
2080 elif self._exp < other._exp and self._sign:
2081 ans = other
2082 elif c == 1:
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00002083 ans = other
Raymond Hettinger636a6b12004-09-19 01:54:09 +00002084
2085 if context is None:
2086 context = getcontext()
Raymond Hettinger76e60d62004-10-20 06:58:28 +00002087 if context._rounding_decision == ALWAYS_ROUND:
2088 return ans._fix(context)
2089 return ans
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00002090
2091 def _isinteger(self):
2092 """Returns whether self is an integer"""
2093 if self._exp >= 0:
2094 return True
2095 rest = self._int[self._exp:]
2096 return rest == (0,)*len(rest)
2097
2098 def _iseven(self):
2099 """Returns 1 if self is even. Assumes self is an integer."""
2100 if self._exp > 0:
2101 return 1
Raymond Hettinger61992ef2004-08-06 23:42:16 +00002102 return self._int[-1+self._exp] & 1 == 0
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00002103
2104 def adjusted(self):
2105 """Return the adjusted exponent of self"""
2106 try:
2107 return self._exp + len(self._int) - 1
2108 #If NaN or Infinity, self._exp is string
2109 except TypeError:
2110 return 0
2111
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00002112 # support for pickling, copy, and deepcopy
2113 def __reduce__(self):
2114 return (self.__class__, (str(self),))
2115
2116 def __copy__(self):
2117 if type(self) == Decimal:
2118 return self # I'm immutable; therefore I am my own clone
2119 return self.__class__(str(self))
2120
2121 def __deepcopy__(self, memo):
2122 if type(self) == Decimal:
2123 return self # My components are also immutable
2124 return self.__class__(str(self))
2125
Raymond Hettingerd9c0a7a2004-07-03 10:02:28 +00002126##### Context class ###########################################
2127
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00002128
2129# get rounding method function:
2130rounding_functions = [name for name in Decimal.__dict__.keys() if name.startswith('_round_')]
2131for name in rounding_functions:
2132 #name is like _round_half_even, goes to the global ROUND_HALF_EVEN value.
2133 globalname = name[1:].upper()
2134 val = globals()[globalname]
2135 Decimal._pick_rounding_function[val] = name
2136
Raymond Hettinger9ec3e3b2004-07-03 13:48:56 +00002137del name, val, globalname, rounding_functions
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00002138
2139class Context(object):
2140 """Contains the context for a Decimal instance.
2141
2142 Contains:
2143 prec - precision (for use in rounding, division, square roots..)
2144 rounding - rounding type. (how you round)
2145 _rounding_decision - ALWAYS_ROUND, NEVER_ROUND -- do you round?
Raymond Hettingerbf440692004-07-10 14:14:37 +00002146 traps - If traps[exception] = 1, then the exception is
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00002147 raised when it is caused. Otherwise, a value is
2148 substituted in.
2149 flags - When an exception is caused, flags[exception] is incremented.
2150 (Whether or not the trap_enabler is set)
2151 Should be reset by user of Decimal instance.
Raymond Hettinger0ea241e2004-07-04 13:53:24 +00002152 Emin - Minimum exponent
2153 Emax - Maximum exponent
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00002154 capitals - If 1, 1*10^1 is printed as 1E+1.
2155 If 0, printed as 1e1
Raymond Hettingere0f15812004-07-05 05:36:39 +00002156 _clamp - If 1, change exponents if too high (Default 0)
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00002157 """
Raymond Hettinger9ec3e3b2004-07-03 13:48:56 +00002158
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00002159 def __init__(self, prec=None, rounding=None,
Raymond Hettingerabf8a562004-10-12 09:12:16 +00002160 traps=None, flags=None,
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00002161 _rounding_decision=None,
Raymond Hettinger0ea241e2004-07-04 13:53:24 +00002162 Emin=None, Emax=None,
Raymond Hettingere0f15812004-07-05 05:36:39 +00002163 capitals=None, _clamp=0,
Raymond Hettingerabf8a562004-10-12 09:12:16 +00002164 _ignored_flags=None):
2165 if flags is None:
2166 flags = []
2167 if _ignored_flags is None:
2168 _ignored_flags = []
Raymond Hettingerbf440692004-07-10 14:14:37 +00002169 if not isinstance(flags, dict):
Raymond Hettingerfed52962004-07-14 15:41:57 +00002170 flags = dict([(s,s in flags) for s in _signals])
Raymond Hettingerb91af522004-07-14 16:35:30 +00002171 del s
Raymond Hettingerbf440692004-07-10 14:14:37 +00002172 if traps is not None and not isinstance(traps, dict):
Raymond Hettingerfed52962004-07-14 15:41:57 +00002173 traps = dict([(s,s in traps) for s in _signals])
Raymond Hettingerb91af522004-07-14 16:35:30 +00002174 del s
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00002175 for name, val in locals().items():
2176 if val is None:
2177 setattr(self, name, copy.copy(getattr(DefaultContext, name)))
2178 else:
2179 setattr(self, name, val)
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00002180 del self.self
2181
Raymond Hettingerb1b605e2004-07-04 01:55:39 +00002182 def __repr__(self):
Raymond Hettingerbf440692004-07-10 14:14:37 +00002183 """Show the current context."""
Raymond Hettingerb1b605e2004-07-04 01:55:39 +00002184 s = []
Raymond Hettingerbf440692004-07-10 14:14:37 +00002185 s.append('Context(prec=%(prec)d, rounding=%(rounding)s, Emin=%(Emin)d, Emax=%(Emax)d, capitals=%(capitals)d' % vars(self))
2186 s.append('flags=[' + ', '.join([f.__name__ for f, v in self.flags.items() if v]) + ']')
2187 s.append('traps=[' + ', '.join([t.__name__ for t, v in self.traps.items() if v]) + ']')
Raymond Hettingerb1b605e2004-07-04 01:55:39 +00002188 return ', '.join(s) + ')'
2189
Raymond Hettingerd9c0a7a2004-07-03 10:02:28 +00002190 def clear_flags(self):
2191 """Reset all flags to zero"""
2192 for flag in self.flags:
Raymond Hettingerb1b605e2004-07-04 01:55:39 +00002193 self.flags[flag] = 0
Raymond Hettingerd9c0a7a2004-07-03 10:02:28 +00002194
Raymond Hettinger9fce44b2004-08-08 04:03:24 +00002195 def _shallow_copy(self):
2196 """Returns a shallow copy from self."""
Raymond Hettingerbf440692004-07-10 14:14:37 +00002197 nc = Context(self.prec, self.rounding, self.traps, self.flags,
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00002198 self._rounding_decision, self.Emin, self.Emax,
2199 self.capitals, self._clamp, self._ignored_flags)
2200 return nc
Raymond Hettinger9fce44b2004-08-08 04:03:24 +00002201
2202 def copy(self):
2203 """Returns a deep copy from self."""
2204 nc = Context(self.prec, self.rounding, self.traps.copy(), self.flags.copy(),
2205 self._rounding_decision, self.Emin, self.Emax,
2206 self.capitals, self._clamp, self._ignored_flags)
2207 return nc
Raymond Hettinger9ec3e3b2004-07-03 13:48:56 +00002208 __copy__ = copy
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00002209
Raymond Hettinger5aa478b2004-07-09 10:02:53 +00002210 def _raise_error(self, condition, explanation = None, *args):
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00002211 """Handles an error
2212
2213 If the flag is in _ignored_flags, returns the default response.
2214 Otherwise, it increments the flag, then, if the corresponding
2215 trap_enabler is set, it reaises the exception. Otherwise, it returns
2216 the default value after incrementing the flag.
2217 """
Raymond Hettinger5aa478b2004-07-09 10:02:53 +00002218 error = _condition_map.get(condition, condition)
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00002219 if error in self._ignored_flags:
2220 #Don't touch the flag
2221 return error().handle(self, *args)
2222
2223 self.flags[error] += 1
Raymond Hettingerbf440692004-07-10 14:14:37 +00002224 if not self.traps[error]:
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00002225 #The errors define how to handle themselves.
Raymond Hettinger5aa478b2004-07-09 10:02:53 +00002226 return condition().handle(self, *args)
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00002227
2228 # Errors should only be risked on copies of the context
2229 #self._ignored_flags = []
2230 raise error, explanation
2231
2232 def _ignore_all_flags(self):
2233 """Ignore all flags, if they are raised"""
Raymond Hettingerfed52962004-07-14 15:41:57 +00002234 return self._ignore_flags(*_signals)
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00002235
2236 def _ignore_flags(self, *flags):
2237 """Ignore the flags, if they are raised"""
2238 # Do not mutate-- This way, copies of a context leave the original
2239 # alone.
2240 self._ignored_flags = (self._ignored_flags + list(flags))
2241 return list(flags)
2242
2243 def _regard_flags(self, *flags):
2244 """Stop ignoring the flags, if they are raised"""
2245 if flags and isinstance(flags[0], (tuple,list)):
2246 flags = flags[0]
2247 for flag in flags:
2248 self._ignored_flags.remove(flag)
2249
Raymond Hettinger5aa478b2004-07-09 10:02:53 +00002250 def __hash__(self):
2251 """A Context cannot be hashed."""
2252 # We inherit object.__hash__, so we must deny this explicitly
2253 raise TypeError, "Cannot hash a Context."
2254
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00002255 def Etiny(self):
2256 """Returns Etiny (= Emin - prec + 1)"""
2257 return int(self.Emin - self.prec + 1)
2258
2259 def Etop(self):
Raymond Hettingere0f15812004-07-05 05:36:39 +00002260 """Returns maximum exponent (= Emax - prec + 1)"""
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00002261 return int(self.Emax - self.prec + 1)
2262
2263 def _set_rounding_decision(self, type):
2264 """Sets the rounding decision.
2265
2266 Sets the rounding decision, and returns the current (previous)
2267 rounding decision. Often used like:
2268
Raymond Hettinger9fce44b2004-08-08 04:03:24 +00002269 context = context._shallow_copy()
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00002270 # That so you don't change the calling context
2271 # if an error occurs in the middle (say DivisionImpossible is raised).
2272
2273 rounding = context._set_rounding_decision(NEVER_ROUND)
2274 instance = instance / Decimal(2)
2275 context._set_rounding_decision(rounding)
2276
2277 This will make it not round for that operation.
2278 """
2279
2280 rounding = self._rounding_decision
2281 self._rounding_decision = type
2282 return rounding
2283
2284 def _set_rounding(self, type):
2285 """Sets the rounding type.
2286
2287 Sets the rounding type, and returns the current (previous)
2288 rounding type. Often used like:
2289
2290 context = context.copy()
2291 # so you don't change the calling context
2292 # if an error occurs in the middle.
2293 rounding = context._set_rounding(ROUND_UP)
2294 val = self.__sub__(other, context=context)
2295 context._set_rounding(rounding)
2296
2297 This will make it round up for that operation.
2298 """
2299 rounding = self.rounding
2300 self.rounding= type
2301 return rounding
2302
Raymond Hettingerfed52962004-07-14 15:41:57 +00002303 def create_decimal(self, num='0'):
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00002304 """Creates a new Decimal instance but using self as context."""
2305 d = Decimal(num, context=self)
Raymond Hettingerdab988d2004-10-09 07:10:44 +00002306 return d._fix(self)
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00002307
2308 #Methods
2309 def abs(self, a):
2310 """Returns the absolute value of the operand.
2311
2312 If the operand is negative, the result is the same as using the minus
2313 operation on the operand. Otherwise, the result is the same as using
2314 the plus operation on the operand.
2315
Raymond Hettinger9ec3e3b2004-07-03 13:48:56 +00002316 >>> ExtendedContext.abs(Decimal('2.1'))
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00002317 Decimal("2.1")
Raymond Hettinger9ec3e3b2004-07-03 13:48:56 +00002318 >>> ExtendedContext.abs(Decimal('-100'))
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00002319 Decimal("100")
Raymond Hettinger9ec3e3b2004-07-03 13:48:56 +00002320 >>> ExtendedContext.abs(Decimal('101.5'))
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00002321 Decimal("101.5")
Raymond Hettinger9ec3e3b2004-07-03 13:48:56 +00002322 >>> ExtendedContext.abs(Decimal('-101.5'))
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00002323 Decimal("101.5")
2324 """
2325 return a.__abs__(context=self)
2326
2327 def add(self, a, b):
2328 """Return the sum of the two operands.
2329
Raymond Hettinger9ec3e3b2004-07-03 13:48:56 +00002330 >>> ExtendedContext.add(Decimal('12'), Decimal('7.00'))
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00002331 Decimal("19.00")
Raymond Hettinger9ec3e3b2004-07-03 13:48:56 +00002332 >>> ExtendedContext.add(Decimal('1E+2'), Decimal('1.01E+4'))
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00002333 Decimal("1.02E+4")
2334 """
2335 return a.__add__(b, context=self)
2336
2337 def _apply(self, a):
Raymond Hettingerdab988d2004-10-09 07:10:44 +00002338 return str(a._fix(self))
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00002339
2340 def compare(self, a, b):
2341 """Compares values numerically.
2342
2343 If the signs of the operands differ, a value representing each operand
2344 ('-1' if the operand is less than zero, '0' if the operand is zero or
2345 negative zero, or '1' if the operand is greater than zero) is used in
2346 place of that operand for the comparison instead of the actual
2347 operand.
2348
2349 The comparison is then effected by subtracting the second operand from
2350 the first and then returning a value according to the result of the
2351 subtraction: '-1' if the result is less than zero, '0' if the result is
2352 zero or negative zero, or '1' if the result is greater than zero.
2353
Raymond Hettinger9ec3e3b2004-07-03 13:48:56 +00002354 >>> ExtendedContext.compare(Decimal('2.1'), Decimal('3'))
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00002355 Decimal("-1")
Raymond Hettinger9ec3e3b2004-07-03 13:48:56 +00002356 >>> ExtendedContext.compare(Decimal('2.1'), Decimal('2.1'))
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00002357 Decimal("0")
Raymond Hettinger9ec3e3b2004-07-03 13:48:56 +00002358 >>> ExtendedContext.compare(Decimal('2.1'), Decimal('2.10'))
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00002359 Decimal("0")
Raymond Hettinger9ec3e3b2004-07-03 13:48:56 +00002360 >>> ExtendedContext.compare(Decimal('3'), Decimal('2.1'))
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00002361 Decimal("1")
Raymond Hettinger9ec3e3b2004-07-03 13:48:56 +00002362 >>> ExtendedContext.compare(Decimal('2.1'), Decimal('-3'))
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00002363 Decimal("1")
Raymond Hettinger9ec3e3b2004-07-03 13:48:56 +00002364 >>> ExtendedContext.compare(Decimal('-3'), Decimal('2.1'))
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00002365 Decimal("-1")
2366 """
2367 return a.compare(b, context=self)
2368
2369 def divide(self, a, b):
2370 """Decimal division in a specified context.
2371
Raymond Hettinger9ec3e3b2004-07-03 13:48:56 +00002372 >>> ExtendedContext.divide(Decimal('1'), Decimal('3'))
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00002373 Decimal("0.333333333")
Raymond Hettinger9ec3e3b2004-07-03 13:48:56 +00002374 >>> ExtendedContext.divide(Decimal('2'), Decimal('3'))
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00002375 Decimal("0.666666667")
Raymond Hettinger9ec3e3b2004-07-03 13:48:56 +00002376 >>> ExtendedContext.divide(Decimal('5'), Decimal('2'))
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00002377 Decimal("2.5")
Raymond Hettinger9ec3e3b2004-07-03 13:48:56 +00002378 >>> ExtendedContext.divide(Decimal('1'), Decimal('10'))
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00002379 Decimal("0.1")
Raymond Hettinger9ec3e3b2004-07-03 13:48:56 +00002380 >>> ExtendedContext.divide(Decimal('12'), Decimal('12'))
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00002381 Decimal("1")
Raymond Hettinger9ec3e3b2004-07-03 13:48:56 +00002382 >>> ExtendedContext.divide(Decimal('8.00'), Decimal('2'))
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00002383 Decimal("4.00")
Raymond Hettinger9ec3e3b2004-07-03 13:48:56 +00002384 >>> ExtendedContext.divide(Decimal('2.400'), Decimal('2.0'))
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00002385 Decimal("1.20")
Raymond Hettinger9ec3e3b2004-07-03 13:48:56 +00002386 >>> ExtendedContext.divide(Decimal('1000'), Decimal('100'))
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00002387 Decimal("10")
Raymond Hettinger9ec3e3b2004-07-03 13:48:56 +00002388 >>> ExtendedContext.divide(Decimal('1000'), Decimal('1'))
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00002389 Decimal("1000")
Raymond Hettinger9ec3e3b2004-07-03 13:48:56 +00002390 >>> ExtendedContext.divide(Decimal('2.40E+6'), Decimal('2'))
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00002391 Decimal("1.20E+6")
2392 """
2393 return a.__div__(b, context=self)
2394
2395 def divide_int(self, a, b):
2396 """Divides two numbers and returns the integer part of the result.
2397
Raymond Hettinger9ec3e3b2004-07-03 13:48:56 +00002398 >>> ExtendedContext.divide_int(Decimal('2'), Decimal('3'))
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00002399 Decimal("0")
Raymond Hettinger9ec3e3b2004-07-03 13:48:56 +00002400 >>> ExtendedContext.divide_int(Decimal('10'), Decimal('3'))
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00002401 Decimal("3")
Raymond Hettinger9ec3e3b2004-07-03 13:48:56 +00002402 >>> ExtendedContext.divide_int(Decimal('1'), Decimal('0.3'))
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00002403 Decimal("3")
2404 """
2405 return a.__floordiv__(b, context=self)
2406
2407 def divmod(self, a, b):
2408 return a.__divmod__(b, context=self)
2409
2410 def max(self, a,b):
2411 """max compares two values numerically and returns the maximum.
2412
2413 If either operand is a NaN then the general rules apply.
2414 Otherwise, the operands are compared as as though by the compare
2415 operation. If they are numerically equal then the left-hand operand
2416 is chosen as the result. Otherwise the maximum (closer to positive
2417 infinity) of the two operands is chosen as the result.
2418
Raymond Hettinger9ec3e3b2004-07-03 13:48:56 +00002419 >>> ExtendedContext.max(Decimal('3'), Decimal('2'))
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00002420 Decimal("3")
Raymond Hettinger9ec3e3b2004-07-03 13:48:56 +00002421 >>> ExtendedContext.max(Decimal('-10'), Decimal('3'))
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00002422 Decimal("3")
Raymond Hettinger9ec3e3b2004-07-03 13:48:56 +00002423 >>> ExtendedContext.max(Decimal('1.0'), Decimal('1'))
Raymond Hettingerd6c700a2004-08-17 06:39:37 +00002424 Decimal("1")
2425 >>> ExtendedContext.max(Decimal('7'), Decimal('NaN'))
2426 Decimal("7")
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00002427 """
2428 return a.max(b, context=self)
2429
2430 def min(self, a,b):
2431 """min compares two values numerically and returns the minimum.
2432
2433 If either operand is a NaN then the general rules apply.
2434 Otherwise, the operands are compared as as though by the compare
2435 operation. If they are numerically equal then the left-hand operand
2436 is chosen as the result. Otherwise the minimum (closer to negative
2437 infinity) of the two operands is chosen as the result.
2438
Raymond Hettinger9ec3e3b2004-07-03 13:48:56 +00002439 >>> ExtendedContext.min(Decimal('3'), Decimal('2'))
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00002440 Decimal("2")
Raymond Hettinger9ec3e3b2004-07-03 13:48:56 +00002441 >>> ExtendedContext.min(Decimal('-10'), Decimal('3'))
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00002442 Decimal("-10")
Raymond Hettinger9ec3e3b2004-07-03 13:48:56 +00002443 >>> ExtendedContext.min(Decimal('1.0'), Decimal('1'))
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00002444 Decimal("1.0")
Raymond Hettingerd6c700a2004-08-17 06:39:37 +00002445 >>> ExtendedContext.min(Decimal('7'), Decimal('NaN'))
2446 Decimal("7")
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00002447 """
2448 return a.min(b, context=self)
2449
2450 def minus(self, a):
2451 """Minus corresponds to unary prefix minus in Python.
2452
2453 The operation is evaluated using the same rules as subtract; the
2454 operation minus(a) is calculated as subtract('0', a) where the '0'
2455 has the same exponent as the operand.
2456
Raymond Hettinger9ec3e3b2004-07-03 13:48:56 +00002457 >>> ExtendedContext.minus(Decimal('1.3'))
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00002458 Decimal("-1.3")
Raymond Hettinger9ec3e3b2004-07-03 13:48:56 +00002459 >>> ExtendedContext.minus(Decimal('-1.3'))
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00002460 Decimal("1.3")
2461 """
2462 return a.__neg__(context=self)
2463
2464 def multiply(self, a, b):
2465 """multiply multiplies two operands.
2466
2467 If either operand is a special value then the general rules apply.
2468 Otherwise, the operands are multiplied together ('long multiplication'),
2469 resulting in a number which may be as long as the sum of the lengths
2470 of the two operands.
2471
Raymond Hettinger9ec3e3b2004-07-03 13:48:56 +00002472 >>> ExtendedContext.multiply(Decimal('1.20'), Decimal('3'))
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00002473 Decimal("3.60")
Raymond Hettinger9ec3e3b2004-07-03 13:48:56 +00002474 >>> ExtendedContext.multiply(Decimal('7'), Decimal('3'))
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00002475 Decimal("21")
Raymond Hettinger9ec3e3b2004-07-03 13:48:56 +00002476 >>> ExtendedContext.multiply(Decimal('0.9'), Decimal('0.8'))
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00002477 Decimal("0.72")
Raymond Hettinger9ec3e3b2004-07-03 13:48:56 +00002478 >>> ExtendedContext.multiply(Decimal('0.9'), Decimal('-0'))
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00002479 Decimal("-0.0")
Raymond Hettinger9ec3e3b2004-07-03 13:48:56 +00002480 >>> ExtendedContext.multiply(Decimal('654321'), Decimal('654321'))
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00002481 Decimal("4.28135971E+11")
2482 """
2483 return a.__mul__(b, context=self)
2484
2485 def normalize(self, a):
Raymond Hettingere0f15812004-07-05 05:36:39 +00002486 """normalize reduces an operand to its simplest form.
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00002487
2488 Essentially a plus operation with all trailing zeros removed from the
2489 result.
2490
Raymond Hettinger9ec3e3b2004-07-03 13:48:56 +00002491 >>> ExtendedContext.normalize(Decimal('2.1'))
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00002492 Decimal("2.1")
Raymond Hettinger9ec3e3b2004-07-03 13:48:56 +00002493 >>> ExtendedContext.normalize(Decimal('-2.0'))
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00002494 Decimal("-2")
Raymond Hettinger9ec3e3b2004-07-03 13:48:56 +00002495 >>> ExtendedContext.normalize(Decimal('1.200'))
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00002496 Decimal("1.2")
Raymond Hettinger9ec3e3b2004-07-03 13:48:56 +00002497 >>> ExtendedContext.normalize(Decimal('-120'))
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00002498 Decimal("-1.2E+2")
Raymond Hettinger9ec3e3b2004-07-03 13:48:56 +00002499 >>> ExtendedContext.normalize(Decimal('120.00'))
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00002500 Decimal("1.2E+2")
Raymond Hettinger9ec3e3b2004-07-03 13:48:56 +00002501 >>> ExtendedContext.normalize(Decimal('0.00'))
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00002502 Decimal("0")
2503 """
2504 return a.normalize(context=self)
2505
2506 def plus(self, a):
2507 """Plus corresponds to unary prefix plus in Python.
2508
2509 The operation is evaluated using the same rules as add; the
2510 operation plus(a) is calculated as add('0', a) where the '0'
2511 has the same exponent as the operand.
2512
Raymond Hettinger9ec3e3b2004-07-03 13:48:56 +00002513 >>> ExtendedContext.plus(Decimal('1.3'))
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00002514 Decimal("1.3")
Raymond Hettinger9ec3e3b2004-07-03 13:48:56 +00002515 >>> ExtendedContext.plus(Decimal('-1.3'))
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00002516 Decimal("-1.3")
2517 """
2518 return a.__pos__(context=self)
2519
2520 def power(self, a, b, modulo=None):
2521 """Raises a to the power of b, to modulo if given.
2522
2523 The right-hand operand must be a whole number whose integer part (after
2524 any exponent has been applied) has no more than 9 digits and whose
2525 fractional part (if any) is all zeros before any rounding. The operand
2526 may be positive, negative, or zero; if negative, the absolute value of
2527 the power is used, and the left-hand operand is inverted (divided into
2528 1) before use.
2529
2530 If the increased precision needed for the intermediate calculations
2531 exceeds the capabilities of the implementation then an Invalid operation
2532 condition is raised.
2533
2534 If, when raising to a negative power, an underflow occurs during the
2535 division into 1, the operation is not halted at that point but
2536 continues.
2537
Raymond Hettinger9ec3e3b2004-07-03 13:48:56 +00002538 >>> ExtendedContext.power(Decimal('2'), Decimal('3'))
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00002539 Decimal("8")
Raymond Hettinger9ec3e3b2004-07-03 13:48:56 +00002540 >>> ExtendedContext.power(Decimal('2'), Decimal('-3'))
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00002541 Decimal("0.125")
Raymond Hettinger9ec3e3b2004-07-03 13:48:56 +00002542 >>> ExtendedContext.power(Decimal('1.7'), Decimal('8'))
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00002543 Decimal("69.7575744")
Raymond Hettinger9ec3e3b2004-07-03 13:48:56 +00002544 >>> ExtendedContext.power(Decimal('Infinity'), Decimal('-2'))
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00002545 Decimal("0")
Raymond Hettinger9ec3e3b2004-07-03 13:48:56 +00002546 >>> ExtendedContext.power(Decimal('Infinity'), Decimal('-1'))
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00002547 Decimal("0")
Raymond Hettinger9ec3e3b2004-07-03 13:48:56 +00002548 >>> ExtendedContext.power(Decimal('Infinity'), Decimal('0'))
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00002549 Decimal("1")
Raymond Hettinger9ec3e3b2004-07-03 13:48:56 +00002550 >>> ExtendedContext.power(Decimal('Infinity'), Decimal('1'))
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00002551 Decimal("Infinity")
Raymond Hettinger9ec3e3b2004-07-03 13:48:56 +00002552 >>> ExtendedContext.power(Decimal('Infinity'), Decimal('2'))
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00002553 Decimal("Infinity")
Raymond Hettinger9ec3e3b2004-07-03 13:48:56 +00002554 >>> ExtendedContext.power(Decimal('-Infinity'), Decimal('-2'))
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00002555 Decimal("0")
Raymond Hettinger9ec3e3b2004-07-03 13:48:56 +00002556 >>> ExtendedContext.power(Decimal('-Infinity'), Decimal('-1'))
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00002557 Decimal("-0")
Raymond Hettinger9ec3e3b2004-07-03 13:48:56 +00002558 >>> ExtendedContext.power(Decimal('-Infinity'), Decimal('0'))
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00002559 Decimal("1")
Raymond Hettinger9ec3e3b2004-07-03 13:48:56 +00002560 >>> ExtendedContext.power(Decimal('-Infinity'), Decimal('1'))
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00002561 Decimal("-Infinity")
Raymond Hettinger9ec3e3b2004-07-03 13:48:56 +00002562 >>> ExtendedContext.power(Decimal('-Infinity'), Decimal('2'))
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00002563 Decimal("Infinity")
Raymond Hettinger9ec3e3b2004-07-03 13:48:56 +00002564 >>> ExtendedContext.power(Decimal('0'), Decimal('0'))
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00002565 Decimal("NaN")
2566 """
2567 return a.__pow__(b, modulo, context=self)
2568
2569 def quantize(self, a, b):
2570 """Returns a value equal to 'a' (rounded) and having the exponent of 'b'.
2571
2572 The coefficient of the result is derived from that of the left-hand
2573 operand. It may be rounded using the current rounding setting (if the
2574 exponent is being increased), multiplied by a positive power of ten (if
2575 the exponent is being decreased), or is unchanged (if the exponent is
2576 already equal to that of the right-hand operand).
2577
2578 Unlike other operations, if the length of the coefficient after the
2579 quantize operation would be greater than precision then an Invalid
2580 operation condition is raised. This guarantees that, unless there is an
2581 error condition, the exponent of the result of a quantize is always
2582 equal to that of the right-hand operand.
2583
2584 Also unlike other operations, quantize will never raise Underflow, even
2585 if the result is subnormal and inexact.
2586
Raymond Hettinger9ec3e3b2004-07-03 13:48:56 +00002587 >>> ExtendedContext.quantize(Decimal('2.17'), Decimal('0.001'))
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00002588 Decimal("2.170")
Raymond Hettinger9ec3e3b2004-07-03 13:48:56 +00002589 >>> ExtendedContext.quantize(Decimal('2.17'), Decimal('0.01'))
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00002590 Decimal("2.17")
Raymond Hettinger9ec3e3b2004-07-03 13:48:56 +00002591 >>> ExtendedContext.quantize(Decimal('2.17'), Decimal('0.1'))
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00002592 Decimal("2.2")
Raymond Hettinger9ec3e3b2004-07-03 13:48:56 +00002593 >>> ExtendedContext.quantize(Decimal('2.17'), Decimal('1e+0'))
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00002594 Decimal("2")
Raymond Hettinger9ec3e3b2004-07-03 13:48:56 +00002595 >>> ExtendedContext.quantize(Decimal('2.17'), Decimal('1e+1'))
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00002596 Decimal("0E+1")
Raymond Hettinger9ec3e3b2004-07-03 13:48:56 +00002597 >>> ExtendedContext.quantize(Decimal('-Inf'), Decimal('Infinity'))
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00002598 Decimal("-Infinity")
Raymond Hettinger9ec3e3b2004-07-03 13:48:56 +00002599 >>> ExtendedContext.quantize(Decimal('2'), Decimal('Infinity'))
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00002600 Decimal("NaN")
Raymond Hettinger9ec3e3b2004-07-03 13:48:56 +00002601 >>> ExtendedContext.quantize(Decimal('-0.1'), Decimal('1'))
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00002602 Decimal("-0")
Raymond Hettinger9ec3e3b2004-07-03 13:48:56 +00002603 >>> ExtendedContext.quantize(Decimal('-0'), Decimal('1e+5'))
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00002604 Decimal("-0E+5")
Raymond Hettinger9ec3e3b2004-07-03 13:48:56 +00002605 >>> ExtendedContext.quantize(Decimal('+35236450.6'), Decimal('1e-2'))
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00002606 Decimal("NaN")
Raymond Hettinger9ec3e3b2004-07-03 13:48:56 +00002607 >>> ExtendedContext.quantize(Decimal('-35236450.6'), Decimal('1e-2'))
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00002608 Decimal("NaN")
Raymond Hettinger9ec3e3b2004-07-03 13:48:56 +00002609 >>> ExtendedContext.quantize(Decimal('217'), Decimal('1e-1'))
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00002610 Decimal("217.0")
Raymond Hettinger9ec3e3b2004-07-03 13:48:56 +00002611 >>> ExtendedContext.quantize(Decimal('217'), Decimal('1e-0'))
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00002612 Decimal("217")
Raymond Hettinger9ec3e3b2004-07-03 13:48:56 +00002613 >>> ExtendedContext.quantize(Decimal('217'), Decimal('1e+1'))
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00002614 Decimal("2.2E+2")
Raymond Hettinger9ec3e3b2004-07-03 13:48:56 +00002615 >>> ExtendedContext.quantize(Decimal('217'), Decimal('1e+2'))
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00002616 Decimal("2E+2")
2617 """
2618 return a.quantize(b, context=self)
2619
2620 def remainder(self, a, b):
2621 """Returns the remainder from integer division.
2622
2623 The result is the residue of the dividend after the operation of
2624 calculating integer division as described for divide-integer, rounded to
2625 precision digits if necessary. The sign of the result, if non-zero, is
2626 the same as that of the original dividend.
2627
2628 This operation will fail under the same conditions as integer division
2629 (that is, if integer division on the same two operands would fail, the
2630 remainder cannot be calculated).
2631
Raymond Hettinger9ec3e3b2004-07-03 13:48:56 +00002632 >>> ExtendedContext.remainder(Decimal('2.1'), Decimal('3'))
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00002633 Decimal("2.1")
Raymond Hettinger9ec3e3b2004-07-03 13:48:56 +00002634 >>> ExtendedContext.remainder(Decimal('10'), Decimal('3'))
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00002635 Decimal("1")
Raymond Hettinger9ec3e3b2004-07-03 13:48:56 +00002636 >>> ExtendedContext.remainder(Decimal('-10'), Decimal('3'))
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00002637 Decimal("-1")
Raymond Hettinger9ec3e3b2004-07-03 13:48:56 +00002638 >>> ExtendedContext.remainder(Decimal('10.2'), Decimal('1'))
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00002639 Decimal("0.2")
Raymond Hettinger9ec3e3b2004-07-03 13:48:56 +00002640 >>> ExtendedContext.remainder(Decimal('10'), Decimal('0.3'))
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00002641 Decimal("0.1")
Raymond Hettinger9ec3e3b2004-07-03 13:48:56 +00002642 >>> ExtendedContext.remainder(Decimal('3.6'), Decimal('1.3'))
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00002643 Decimal("1.0")
2644 """
2645 return a.__mod__(b, context=self)
2646
2647 def remainder_near(self, a, b):
2648 """Returns to be "a - b * n", where n is the integer nearest the exact
2649 value of "x / b" (if two integers are equally near then the even one
2650 is chosen). If the result is equal to 0 then its sign will be the
2651 sign of a.
2652
2653 This operation will fail under the same conditions as integer division
2654 (that is, if integer division on the same two operands would fail, the
2655 remainder cannot be calculated).
2656
Raymond Hettinger9ec3e3b2004-07-03 13:48:56 +00002657 >>> ExtendedContext.remainder_near(Decimal('2.1'), Decimal('3'))
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00002658 Decimal("-0.9")
Raymond Hettinger9ec3e3b2004-07-03 13:48:56 +00002659 >>> ExtendedContext.remainder_near(Decimal('10'), Decimal('6'))
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00002660 Decimal("-2")
Raymond Hettinger9ec3e3b2004-07-03 13:48:56 +00002661 >>> ExtendedContext.remainder_near(Decimal('10'), Decimal('3'))
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00002662 Decimal("1")
Raymond Hettinger9ec3e3b2004-07-03 13:48:56 +00002663 >>> ExtendedContext.remainder_near(Decimal('-10'), Decimal('3'))
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00002664 Decimal("-1")
Raymond Hettinger9ec3e3b2004-07-03 13:48:56 +00002665 >>> ExtendedContext.remainder_near(Decimal('10.2'), Decimal('1'))
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00002666 Decimal("0.2")
Raymond Hettinger9ec3e3b2004-07-03 13:48:56 +00002667 >>> ExtendedContext.remainder_near(Decimal('10'), Decimal('0.3'))
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00002668 Decimal("0.1")
Raymond Hettinger9ec3e3b2004-07-03 13:48:56 +00002669 >>> ExtendedContext.remainder_near(Decimal('3.6'), Decimal('1.3'))
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00002670 Decimal("-0.3")
2671 """
2672 return a.remainder_near(b, context=self)
2673
2674 def same_quantum(self, a, b):
2675 """Returns True if the two operands have the same exponent.
2676
2677 The result is never affected by either the sign or the coefficient of
2678 either operand.
2679
Raymond Hettinger9ec3e3b2004-07-03 13:48:56 +00002680 >>> ExtendedContext.same_quantum(Decimal('2.17'), Decimal('0.001'))
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00002681 False
Raymond Hettinger9ec3e3b2004-07-03 13:48:56 +00002682 >>> ExtendedContext.same_quantum(Decimal('2.17'), Decimal('0.01'))
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00002683 True
Raymond Hettinger9ec3e3b2004-07-03 13:48:56 +00002684 >>> ExtendedContext.same_quantum(Decimal('2.17'), Decimal('1'))
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00002685 False
Raymond Hettinger9ec3e3b2004-07-03 13:48:56 +00002686 >>> ExtendedContext.same_quantum(Decimal('Inf'), Decimal('-Inf'))
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00002687 True
2688 """
2689 return a.same_quantum(b)
2690
2691 def sqrt(self, a):
2692 """Returns the square root of a non-negative number to context precision.
2693
2694 If the result must be inexact, it is rounded using the round-half-even
2695 algorithm.
2696
Raymond Hettinger9ec3e3b2004-07-03 13:48:56 +00002697 >>> ExtendedContext.sqrt(Decimal('0'))
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00002698 Decimal("0")
Raymond Hettinger9ec3e3b2004-07-03 13:48:56 +00002699 >>> ExtendedContext.sqrt(Decimal('-0'))
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00002700 Decimal("-0")
Raymond Hettinger9ec3e3b2004-07-03 13:48:56 +00002701 >>> ExtendedContext.sqrt(Decimal('0.39'))
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00002702 Decimal("0.624499800")
Raymond Hettinger9ec3e3b2004-07-03 13:48:56 +00002703 >>> ExtendedContext.sqrt(Decimal('100'))
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00002704 Decimal("10")
Raymond Hettinger9ec3e3b2004-07-03 13:48:56 +00002705 >>> ExtendedContext.sqrt(Decimal('1'))
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00002706 Decimal("1")
Raymond Hettinger9ec3e3b2004-07-03 13:48:56 +00002707 >>> ExtendedContext.sqrt(Decimal('1.0'))
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00002708 Decimal("1.0")
Raymond Hettinger9ec3e3b2004-07-03 13:48:56 +00002709 >>> ExtendedContext.sqrt(Decimal('1.00'))
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00002710 Decimal("1.0")
Raymond Hettinger9ec3e3b2004-07-03 13:48:56 +00002711 >>> ExtendedContext.sqrt(Decimal('7'))
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00002712 Decimal("2.64575131")
Raymond Hettinger9ec3e3b2004-07-03 13:48:56 +00002713 >>> ExtendedContext.sqrt(Decimal('10'))
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00002714 Decimal("3.16227766")
Raymond Hettinger9ec3e3b2004-07-03 13:48:56 +00002715 >>> ExtendedContext.prec
Raymond Hettinger6ea48452004-07-03 12:26:21 +00002716 9
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00002717 """
2718 return a.sqrt(context=self)
2719
2720 def subtract(self, a, b):
2721 """Return the sum of the two operands.
2722
Raymond Hettinger9ec3e3b2004-07-03 13:48:56 +00002723 >>> ExtendedContext.subtract(Decimal('1.3'), Decimal('1.07'))
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00002724 Decimal("0.23")
Raymond Hettinger9ec3e3b2004-07-03 13:48:56 +00002725 >>> ExtendedContext.subtract(Decimal('1.3'), Decimal('1.30'))
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00002726 Decimal("0.00")
Raymond Hettinger9ec3e3b2004-07-03 13:48:56 +00002727 >>> ExtendedContext.subtract(Decimal('1.3'), Decimal('2.07'))
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00002728 Decimal("-0.77")
2729 """
2730 return a.__sub__(b, context=self)
2731
2732 def to_eng_string(self, a):
2733 """Converts a number to a string, using scientific notation.
2734
2735 The operation is not affected by the context.
2736 """
2737 return a.to_eng_string(context=self)
2738
2739 def to_sci_string(self, a):
2740 """Converts a number to a string, using scientific notation.
2741
2742 The operation is not affected by the context.
2743 """
2744 return a.__str__(context=self)
2745
2746 def to_integral(self, a):
2747 """Rounds to an integer.
2748
2749 When the operand has a negative exponent, the result is the same
2750 as using the quantize() operation using the given operand as the
2751 left-hand-operand, 1E+0 as the right-hand-operand, and the precision
2752 of the operand as the precision setting, except that no flags will
2753 be set. The rounding mode is taken from the context.
2754
Raymond Hettinger9ec3e3b2004-07-03 13:48:56 +00002755 >>> ExtendedContext.to_integral(Decimal('2.1'))
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00002756 Decimal("2")
Raymond Hettinger9ec3e3b2004-07-03 13:48:56 +00002757 >>> ExtendedContext.to_integral(Decimal('100'))
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00002758 Decimal("100")
Raymond Hettinger9ec3e3b2004-07-03 13:48:56 +00002759 >>> ExtendedContext.to_integral(Decimal('100.0'))
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00002760 Decimal("100")
Raymond Hettinger9ec3e3b2004-07-03 13:48:56 +00002761 >>> ExtendedContext.to_integral(Decimal('101.5'))
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00002762 Decimal("102")
Raymond Hettinger9ec3e3b2004-07-03 13:48:56 +00002763 >>> ExtendedContext.to_integral(Decimal('-101.5'))
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00002764 Decimal("-102")
Raymond Hettinger9ec3e3b2004-07-03 13:48:56 +00002765 >>> ExtendedContext.to_integral(Decimal('10E+5'))
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00002766 Decimal("1.0E+6")
Raymond Hettinger9ec3e3b2004-07-03 13:48:56 +00002767 >>> ExtendedContext.to_integral(Decimal('7.89E+77'))
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00002768 Decimal("7.89E+77")
Raymond Hettinger9ec3e3b2004-07-03 13:48:56 +00002769 >>> ExtendedContext.to_integral(Decimal('-Inf'))
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00002770 Decimal("-Infinity")
2771 """
2772 return a.to_integral(context=self)
2773
2774class _WorkRep(object):
2775 __slots__ = ('sign','int','exp')
Raymond Hettinger17931de2004-10-27 06:21:46 +00002776 # sign: 0 or 1
Raymond Hettinger636a6b12004-09-19 01:54:09 +00002777 # int: int or long
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00002778 # exp: None, int, or string
2779
2780 def __init__(self, value=None):
2781 if value is None:
2782 self.sign = None
Raymond Hettinger636a6b12004-09-19 01:54:09 +00002783 self.int = 0
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00002784 self.exp = None
Raymond Hettinger17931de2004-10-27 06:21:46 +00002785 elif isinstance(value, Decimal):
2786 self.sign = value._sign
Raymond Hettinger636a6b12004-09-19 01:54:09 +00002787 cum = 0
Raymond Hettinger17931de2004-10-27 06:21:46 +00002788 for digit in value._int:
Raymond Hettinger636a6b12004-09-19 01:54:09 +00002789 cum = cum * 10 + digit
2790 self.int = cum
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00002791 self.exp = value._exp
Raymond Hettinger17931de2004-10-27 06:21:46 +00002792 else:
2793 # assert isinstance(value, tuple)
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00002794 self.sign = value[0]
2795 self.int = value[1]
2796 self.exp = value[2]
2797
2798 def __repr__(self):
2799 return "(%r, %r, %r)" % (self.sign, self.int, self.exp)
2800
2801 __str__ = __repr__
2802
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00002803
2804
2805def _normalize(op1, op2, shouldround = 0, prec = 0):
2806 """Normalizes op1, op2 to have the same exp and length of coefficient.
2807
2808 Done during addition.
2809 """
2810 # Yes, the exponent is a long, but the difference between exponents
2811 # must be an int-- otherwise you'd get a big memory problem.
2812 numdigits = int(op1.exp - op2.exp)
2813 if numdigits < 0:
2814 numdigits = -numdigits
2815 tmp = op2
2816 other = op1
2817 else:
2818 tmp = op1
2819 other = op2
2820
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00002821
Raymond Hettinger636a6b12004-09-19 01:54:09 +00002822 if shouldround and numdigits > prec + 1:
2823 # Big difference in exponents - check the adjusted exponents
2824 tmp_len = len(str(tmp.int))
2825 other_len = len(str(other.int))
2826 if numdigits > (other_len + prec + 1 - tmp_len):
2827 # If the difference in adjusted exps is > prec+1, we know
2828 # other is insignificant, so might as well put a 1 after the precision.
2829 # (since this is only for addition.) Also stops use of massive longs.
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00002830
Raymond Hettinger636a6b12004-09-19 01:54:09 +00002831 extend = prec + 2 - tmp_len
2832 if extend <= 0:
2833 extend = 1
2834 tmp.int *= 10 ** extend
2835 tmp.exp -= extend
2836 other.int = 1
2837 other.exp = tmp.exp
2838 return op1, op2
2839
2840 tmp.int *= 10 ** numdigits
2841 tmp.exp -= numdigits
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00002842 return op1, op2
2843
2844def _adjust_coefficients(op1, op2):
Raymond Hettinger636a6b12004-09-19 01:54:09 +00002845 """Adjust op1, op2 so that op2.int * 10 > op1.int >= op2.int.
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00002846
2847 Returns the adjusted op1, op2 as well as the change in op1.exp-op2.exp.
2848
2849 Used on _WorkRep instances during division.
2850 """
2851 adjust = 0
Raymond Hettinger636a6b12004-09-19 01:54:09 +00002852 #If op1 is smaller, make it larger
2853 while op2.int > op1.int:
2854 op1.int *= 10
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00002855 op1.exp -= 1
Raymond Hettinger636a6b12004-09-19 01:54:09 +00002856 adjust += 1
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00002857
Raymond Hettinger636a6b12004-09-19 01:54:09 +00002858 #If op2 is too small, make it larger
2859 while op1.int >= (10 * op2.int):
2860 op2.int *= 10
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00002861 op2.exp -= 1
2862 adjust -= 1
Raymond Hettinger636a6b12004-09-19 01:54:09 +00002863
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00002864 return op1, op2, adjust
2865
2866##### Helper Functions ########################################
2867
Raymond Hettinger636a6b12004-09-19 01:54:09 +00002868def _convert_other(other):
2869 """Convert other to Decimal.
2870
2871 Verifies that it's ok to use in an implicit construction.
2872 """
2873 if isinstance(other, Decimal):
2874 return other
2875 if isinstance(other, (int, long)):
2876 return Decimal(other)
2877
2878 raise TypeError, "You can interact Decimal only with int, long or Decimal data types."
2879
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00002880_infinity_map = {
2881 'inf' : 1,
2882 'infinity' : 1,
2883 '+inf' : 1,
2884 '+infinity' : 1,
2885 '-inf' : -1,
2886 '-infinity' : -1
2887}
2888
Raymond Hettinger0ea241e2004-07-04 13:53:24 +00002889def _isinfinity(num):
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00002890 """Determines whether a string or float is infinity.
2891
Raymond Hettinger0ea241e2004-07-04 13:53:24 +00002892 +1 for negative infinity; 0 for finite ; +1 for positive infinity
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00002893 """
2894 num = str(num).lower()
2895 return _infinity_map.get(num, 0)
2896
Raymond Hettinger0ea241e2004-07-04 13:53:24 +00002897def _isnan(num):
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00002898 """Determines whether a string or float is NaN
2899
2900 (1, sign, diagnostic info as string) => NaN
2901 (2, sign, diagnostic info as string) => sNaN
2902 0 => not a NaN
2903 """
2904 num = str(num).lower()
2905 if not num:
2906 return 0
2907
2908 #get the sign, get rid of trailing [+-]
2909 sign = 0
2910 if num[0] == '+':
2911 num = num[1:]
2912 elif num[0] == '-': #elif avoids '+-nan'
2913 num = num[1:]
2914 sign = 1
2915
2916 if num.startswith('nan'):
2917 if len(num) > 3 and not num[3:].isdigit(): #diagnostic info
2918 return 0
2919 return (1, sign, num[3:].lstrip('0'))
2920 if num.startswith('snan'):
2921 if len(num) > 4 and not num[4:].isdigit():
2922 return 0
2923 return (2, sign, num[4:].lstrip('0'))
2924 return 0
2925
2926
2927##### Setup Specific Contexts ################################
2928
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00002929# The default context prototype used by Context()
Raymond Hettingerfed52962004-07-14 15:41:57 +00002930# Is mutable, so that new contexts can have different default values
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00002931
2932DefaultContext = Context(
Raymond Hettinger6ea48452004-07-03 12:26:21 +00002933 prec=28, rounding=ROUND_HALF_EVEN,
Raymond Hettingerbf440692004-07-10 14:14:37 +00002934 traps=[DivisionByZero, Overflow, InvalidOperation],
2935 flags=[],
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00002936 _rounding_decision=ALWAYS_ROUND,
Raymond Hettinger99148e72004-07-14 19:56:56 +00002937 Emax=999999999,
2938 Emin=-999999999,
Raymond Hettingere0f15812004-07-05 05:36:39 +00002939 capitals=1
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00002940)
2941
2942# Pre-made alternate contexts offered by the specification
2943# Don't change these; the user should be able to select these
2944# contexts and be able to reproduce results from other implementations
2945# of the spec.
2946
Raymond Hettinger9ec3e3b2004-07-03 13:48:56 +00002947BasicContext = Context(
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00002948 prec=9, rounding=ROUND_HALF_UP,
Raymond Hettingerbf440692004-07-10 14:14:37 +00002949 traps=[DivisionByZero, Overflow, InvalidOperation, Clamped, Underflow],
2950 flags=[],
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00002951)
2952
Raymond Hettinger9ec3e3b2004-07-03 13:48:56 +00002953ExtendedContext = Context(
Raymond Hettinger6ea48452004-07-03 12:26:21 +00002954 prec=9, rounding=ROUND_HALF_EVEN,
Raymond Hettingerbf440692004-07-10 14:14:37 +00002955 traps=[],
2956 flags=[],
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00002957)
2958
2959
Raymond Hettingerd9c0a7a2004-07-03 10:02:28 +00002960##### Useful Constants (internal use only) ####################
Raymond Hettinger7c85fa42004-07-01 11:01:35 +00002961
2962#Reusable defaults
2963Inf = Decimal('Inf')
2964negInf = Decimal('-Inf')
2965
2966#Infsign[sign] is infinity w/ that sign
2967Infsign = (Inf, negInf)
2968
2969NaN = Decimal('NaN')
2970
2971
2972##### crud for parsing strings #################################
2973import re
2974
2975# There's an optional sign at the start, and an optional exponent
2976# at the end. The exponent has an optional sign and at least one
2977# digit. In between, must have either at least one digit followed
2978# by an optional fraction, or a decimal point followed by at least
2979# one digit. Yuck.
2980
2981_parser = re.compile(r"""
2982# \s*
2983 (?P<sign>[-+])?
2984 (
2985 (?P<int>\d+) (\. (?P<frac>\d*))?
2986 |
2987 \. (?P<onlyfrac>\d+)
2988 )
2989 ([eE](?P<exp>[-+]? \d+))?
2990# \s*
2991 $
2992""", re.VERBOSE).match #Uncomment the \s* to allow leading or trailing spaces.
2993
2994del re
2995
2996# return sign, n, p s.t. float string value == -1**sign * n * 10**p exactly
2997
2998def _string2exact(s):
2999 m = _parser(s)
3000 if m is None:
3001 raise ValueError("invalid literal for Decimal: %r" % s)
3002
3003 if m.group('sign') == "-":
3004 sign = 1
3005 else:
3006 sign = 0
3007
3008 exp = m.group('exp')
3009 if exp is None:
3010 exp = 0
3011 else:
3012 exp = int(exp)
3013
3014 intpart = m.group('int')
3015 if intpart is None:
3016 intpart = ""
3017 fracpart = m.group('onlyfrac')
3018 else:
3019 fracpart = m.group('frac')
3020 if fracpart is None:
3021 fracpart = ""
3022
3023 exp -= len(fracpart)
3024
3025 mantissa = intpart + fracpart
3026 tmp = map(int, mantissa)
3027 backup = tmp
3028 while tmp and tmp[0] == 0:
3029 del tmp[0]
3030
3031 # It's a zero
3032 if not tmp:
3033 if backup:
3034 return (sign, tuple(backup), exp)
3035 return (sign, (0,), exp)
3036 mantissa = tuple(tmp)
3037
3038 return (sign, mantissa, exp)
3039
3040
3041if __name__ == '__main__':
3042 import doctest, sys
3043 doctest.testmod(sys.modules[__name__])