Rietveld Code Review Tool
Help | Bug tracker | Discussion group | Source code | Sign in
(65541)

Delta Between Two Patch Sets: Lib/decimal.py

Issue 7652: Merge C version of decimal into py3k.
Left Patch Set: Created 7 years, 10 months ago
Right Patch Set: Created 7 years, 7 months ago
Left:
Right:
Use n/p to move between diff chunks; N/P to move between comments. Please Sign in to add in-line comments.
Jump to:
Left: Side by side diff | Download
Right: Side by side diff | Download
« no previous file with change/comment | « Include/longintrepr.h ('k') | Lib/test/support.py » ('j') | no next file with change/comment »
Toggle Intra-line Diffs ('i') | Expand Comments ('e') | Collapse Comments ('c') | Show Comments Hide Comments ('s')
LEFTRIGHT
1 # Copyright (c) 2004 Python Software Foundation. 1 # Copyright (c) 2004 Python Software Foundation.
2 # All rights reserved. 2 # All rights reserved.
3 3
4 # Written by Eric Price <eprice at tjhsst.edu> 4 # Written by Eric Price <eprice at tjhsst.edu>
5 # and Facundo Batista <facundo at taniquetil.com.ar> 5 # and Facundo Batista <facundo at taniquetil.com.ar>
6 # and Raymond Hettinger <python at rcn.com> 6 # and Raymond Hettinger <python at rcn.com>
7 # and Aahz <aahz at pobox.com> 7 # and Aahz <aahz at pobox.com>
8 # and Tim Peters 8 # and Tim Peters
9 9
10 # This module should be kept in sync with the latest updates of the 10 # This module should be kept in sync with the latest updates of the
(...skipping 110 matching lines...) Expand 10 before | Expand all | Expand 10 after
121 121
122 # Exceptions 122 # Exceptions
123 'DecimalException', 'Clamped', 'InvalidOperation', 'DivisionByZero', 123 'DecimalException', 'Clamped', 'InvalidOperation', 'DivisionByZero',
124 'Inexact', 'Rounded', 'Subnormal', 'Overflow', 'Underflow', 124 'Inexact', 'Rounded', 'Subnormal', 'Overflow', 'Underflow',
125 125
126 # Constants for use in setting up contexts 126 # Constants for use in setting up contexts
127 'ROUND_DOWN', 'ROUND_HALF_UP', 'ROUND_HALF_EVEN', 'ROUND_CEILING', 127 'ROUND_DOWN', 'ROUND_HALF_UP', 'ROUND_HALF_EVEN', 'ROUND_CEILING',
128 'ROUND_FLOOR', 'ROUND_UP', 'ROUND_HALF_DOWN', 'ROUND_05UP', 128 'ROUND_FLOOR', 'ROUND_UP', 'ROUND_HALF_DOWN', 'ROUND_05UP',
129 129
130 # Functions for manipulating contexts 130 # Functions for manipulating contexts
131 'setcontext', 'getcontext', 'localcontext' 131 'setcontext', 'getcontext', 'localcontext',
132
133 # Limits for the C version for compatibility
134 'MAX_PREC', 'MAX_EMAX', 'MIN_EMIN', 'MIN_ETINY',
135
136 # C version: compile time choice that enables the thread local context
137 'HAVE_THREADS'
132 ] 138 ]
133 139
134 __version__ = '1.70' # Highest version of the spec this complies with 140 __version__ = '1.70' # Highest version of the spec this complies with
135 # See http://speleotrove.com/decimal/ 141 # See http://speleotrove.com/decimal/
136 142
137 import copy as _copy 143 import copy as _copy
138 import math as _math 144 import math as _math
139 import numbers as _numbers 145 import numbers as _numbers
146 import sys
140 147
141 try: 148 try:
142 from collections import namedtuple as _namedtuple 149 from collections import namedtuple as _namedtuple
143 DecimalTuple = _namedtuple('DecimalTuple', 'sign digits exponent') 150 DecimalTuple = _namedtuple('DecimalTuple', 'sign digits exponent')
144 except ImportError: 151 except ImportError:
145 DecimalTuple = lambda *args: args 152 DecimalTuple = lambda *args: args
146 153
147 # Rounding 154 # Rounding
148 ROUND_DOWN = 'ROUND_DOWN' 155 ROUND_DOWN = 'ROUND_DOWN'
149 ROUND_HALF_UP = 'ROUND_HALF_UP' 156 ROUND_HALF_UP = 'ROUND_HALF_UP'
150 ROUND_HALF_EVEN = 'ROUND_HALF_EVEN' 157 ROUND_HALF_EVEN = 'ROUND_HALF_EVEN'
151 ROUND_CEILING = 'ROUND_CEILING' 158 ROUND_CEILING = 'ROUND_CEILING'
152 ROUND_FLOOR = 'ROUND_FLOOR' 159 ROUND_FLOOR = 'ROUND_FLOOR'
153 ROUND_UP = 'ROUND_UP' 160 ROUND_UP = 'ROUND_UP'
154 ROUND_HALF_DOWN = 'ROUND_HALF_DOWN' 161 ROUND_HALF_DOWN = 'ROUND_HALF_DOWN'
155 ROUND_05UP = 'ROUND_05UP' 162 ROUND_05UP = 'ROUND_05UP'
163
164 # Compatibility with the C version
165 HAVE_THREADS = True
166 if sys.maxsize == 2**63-1:
167 MAX_PREC = 999999999999999999
168 MAX_EMAX = 999999999999999999
169 MIN_EMIN = -999999999999999999
170 else:
171 MAX_PREC = 425000000
172 MAX_EMAX = 425000000
173 MIN_EMIN = -425000000
174
175 MIN_ETINY = MIN_EMIN - (MAX_PREC-1)
156 176
157 # Errors 177 # Errors
158 178
159 class DecimalException(ArithmeticError): 179 class DecimalException(ArithmeticError):
160 """Base exception class. 180 """Base exception class.
161 181
162 Used exceptions derive from this. 182 Used exceptions derive from this.
163 If an exception derives from another exception besides this (such as 183 If an exception derives from another exception besides this (such as
164 Underflow (Inexact, Rounded, Subnormal) that indicates that it is only 184 Underflow (Inexact, Rounded, Subnormal) that indicates that it is only
165 called if the others are present. This isn't actually used for 185 called if the others are present. This isn't actually used for
(...skipping 223 matching lines...) Expand 10 before | Expand all | Expand 10 after
389 # The getcontext() and setcontext() function manage access to a thread-local 409 # The getcontext() and setcontext() function manage access to a thread-local
390 # current context. Py2.4 offers direct support for thread locals. If that 410 # current context. Py2.4 offers direct support for thread locals. If that
391 # is not available, use threading.current_thread() which is slower but will 411 # is not available, use threading.current_thread() which is slower but will
392 # work for older Pythons. If threads are not part of the build, create a 412 # work for older Pythons. If threads are not part of the build, create a
393 # mock threading object with threading.local() returning the module namespace. 413 # mock threading object with threading.local() returning the module namespace.
394 414
395 try: 415 try:
396 import threading 416 import threading
397 except ImportError: 417 except ImportError:
398 # Python was compiled without threads; create a mock object instead 418 # Python was compiled without threads; create a mock object instead
399 import sys
400 class MockThreading(object): 419 class MockThreading(object):
401 def local(self, sys=sys): 420 def local(self, sys=sys):
402 return sys.modules[__name__] 421 return sys.modules[__name__]
403 threading = MockThreading() 422 threading = MockThreading()
404 del sys, MockThreading 423 del MockThreading
405 424
406 try: 425 try:
407 threading.local 426 threading.local
408 427
409 except AttributeError: 428 except AttributeError:
410 429
411 # To fix reloading, force it to create a new context 430 # To fix reloading, force it to create a new context
412 # Old contexts have different exceptions in their dicts, making problems. 431 # Old contexts have different exceptions in their dicts, making problems.
413 if hasattr(threading.current_thread(), '__decimal_context__'): 432 if hasattr(threading.current_thread(), '__decimal_context__'):
414 del threading.current_thread().__decimal_context__ 433 del threading.current_thread().__decimal_context__
(...skipping 3532 matching lines...) Expand 10 before | Expand all | Expand 10 after
3947 s.append('flags=[' + ', '.join(names) + ']') 3966 s.append('flags=[' + ', '.join(names) + ']')
3948 names = [t.__name__ for t, v in self.traps.items() if v] 3967 names = [t.__name__ for t, v in self.traps.items() if v]
3949 s.append('traps=[' + ', '.join(names) + ']') 3968 s.append('traps=[' + ', '.join(names) + ']')
3950 return ', '.join(s) + ')' 3969 return ', '.join(s) + ')'
3951 3970
3952 def clear_flags(self): 3971 def clear_flags(self):
3953 """Reset all flags to zero""" 3972 """Reset all flags to zero"""
3954 for flag in self.flags: 3973 for flag in self.flags:
3955 self.flags[flag] = 0 3974 self.flags[flag] = 0
3956 3975
3976 def clear_traps(self):
3977 """Reset all traps to zero"""
3978 for flag in self.traps:
3979 self.traps[flag] = 0
3980
3957 def _shallow_copy(self): 3981 def _shallow_copy(self):
3958 """Returns a shallow copy from self.""" 3982 """Returns a shallow copy from self."""
3959 nc = Context(self.prec, self.rounding, self.Emin, self.Emax, 3983 nc = Context(self.prec, self.rounding, self.Emin, self.Emax,
3960 self.capitals, self.clamp, self.flags, self.traps, 3984 self.capitals, self.clamp, self.flags, self.traps,
3961 self._ignored_flags) 3985 self._ignored_flags)
3962 return nc 3986 return nc
3963 3987
3964 def copy(self): 3988 def copy(self):
3965 """Returns a deep copy from self.""" 3989 """Returns a deep copy from self."""
3966 nc = Context(self.prec, self.rounding, self.Emin, self.Emax, 3990 nc = Context(self.prec, self.rounding, self.Emin, self.Emax,
(...skipping 2177 matching lines...) Expand 10 before | Expand all | Expand 10 after
6144 format_dict['sign'] = '-' 6168 format_dict['sign'] = '-'
6145 6169
6146 # minimumwidth defaults to 0; precision remains None if not given 6170 # minimumwidth defaults to 0; precision remains None if not given
6147 format_dict['minimumwidth'] = int(format_dict['minimumwidth'] or '0') 6171 format_dict['minimumwidth'] = int(format_dict['minimumwidth'] or '0')
6148 if format_dict['precision'] is not None: 6172 if format_dict['precision'] is not None:
6149 format_dict['precision'] = int(format_dict['precision']) 6173 format_dict['precision'] = int(format_dict['precision'])
6150 6174
6151 # if format type is 'g' or 'G' then a precision of 0 makes little 6175 # if format type is 'g' or 'G' then a precision of 0 makes little
6152 # sense; convert it to 1. Same if format type is unspecified. 6176 # sense; convert it to 1. Same if format type is unspecified.
6153 if format_dict['precision'] == 0: 6177 if format_dict['precision'] == 0:
6154 if format_dict['type'] is None or format_dict['type'] in 'gG': 6178 if format_dict['type'] is None or format_dict['type'] in 'gGn':
6155 format_dict['precision'] = 1 6179 format_dict['precision'] = 1
6156 6180
6157 # determine thousands separator, grouping, and decimal separator, and 6181 # determine thousands separator, grouping, and decimal separator, and
6158 # add appropriate entries to format_dict 6182 # add appropriate entries to format_dict
6159 if format_dict['type'] == 'n': 6183 if format_dict['type'] == 'n':
6160 # apart from separators, 'n' behaves just like 'g' 6184 # apart from separators, 'n' behaves just like 'g'
6161 format_dict['type'] = 'g' 6185 format_dict['type'] = 'g'
6162 if _localeconv is None: 6186 if _localeconv is None:
6163 _localeconv = _locale.localeconv() 6187 _localeconv = _locale.localeconv()
6164 if format_dict['thousands_sep'] is not None: 6188 if format_dict['thousands_sep'] is not None:
(...skipping 153 matching lines...) Expand 10 before | Expand all | Expand 10 after
6318 _NaN = Decimal('NaN') 6342 _NaN = Decimal('NaN')
6319 _Zero = Decimal(0) 6343 _Zero = Decimal(0)
6320 _One = Decimal(1) 6344 _One = Decimal(1)
6321 _NegativeOne = Decimal(-1) 6345 _NegativeOne = Decimal(-1)
6322 6346
6323 # _SignedInfinity[sign] is infinity w/ that sign 6347 # _SignedInfinity[sign] is infinity w/ that sign
6324 _SignedInfinity = (_Infinity, _NegativeInfinity) 6348 _SignedInfinity = (_Infinity, _NegativeInfinity)
6325 6349
6326 # Constants related to the hash implementation; hash(x) is based 6350 # Constants related to the hash implementation; hash(x) is based
6327 # on the reduction of x modulo _PyHASH_MODULUS 6351 # on the reduction of x modulo _PyHASH_MODULUS
6328 import sys
6329 _PyHASH_MODULUS = sys.hash_info.modulus 6352 _PyHASH_MODULUS = sys.hash_info.modulus
6330 # hash values to use for positive and negative infinities, and nans 6353 # hash values to use for positive and negative infinities, and nans
6331 _PyHASH_INF = sys.hash_info.inf 6354 _PyHASH_INF = sys.hash_info.inf
6332 _PyHASH_NAN = sys.hash_info.nan 6355 _PyHASH_NAN = sys.hash_info.nan
6333 6356
6334 # _PyHASH_10INV is the inverse of 10 modulo the prime _PyHASH_MODULUS 6357 # _PyHASH_10INV is the inverse of 10 modulo the prime _PyHASH_MODULUS
6335 _PyHASH_10INV = pow(10, _PyHASH_MODULUS - 2, _PyHASH_MODULUS) 6358 _PyHASH_10INV = pow(10, _PyHASH_MODULUS - 2, _PyHASH_MODULUS)
6336 del sys 6359 del sys
6337 6360
6338 try: 6361 try:
6339 import _decimal 6362 import _decimal
6340 except ImportError: 6363 except ImportError:
6341 pass 6364 pass
6342 else: 6365 else:
6343 s1 = set(dir()) 6366 s1 = set(dir())
6344 s2 = set(dir(_decimal)) 6367 s2 = set(dir(_decimal))
6345 for name in s1 - s2: 6368 for name in s1 - s2:
6346 del globals()[name] 6369 del globals()[name]
6347 del s1, s2, name 6370 del s1, s2, name
6348 from _decimal import * 6371 from _decimal import *
6349 6372
6350 if __name__ == '__main__': 6373 if __name__ == '__main__':
6351 import doctest, decimal 6374 import doctest, decimal
6352 doctest.testmod(decimal) 6375 doctest.testmod(decimal)
LEFTRIGHT

RSS Feeds Recent Issues | This issue
This is Rietveld 894c83f36cb7+