[pypy-commit] pypy faster-str-of-bigint: use a string builder
cfbolz
noreply at buildbot.pypy.org
Wed Jun 26 09:03:52 CEST 2013
Author: Carl Friedrich Bolz <cfbolz at gmx.de>
Branch: faster-str-of-bigint
Changeset: r64993:c18866b5ecce
Date: 2013-06-25 22:21 +0200
http://bitbucket.org/pypy/pypy/changeset/c18866b5ecce/
Log: use a string builder
diff --git a/rpython/rlib/rbigint.py b/rpython/rlib/rbigint.py
--- a/rpython/rlib/rbigint.py
+++ b/rpython/rlib/rbigint.py
@@ -2191,15 +2191,26 @@
_FORMAT_DECIMAL_MINDIGITS = 9 # fits in 32 bits, there may be a better choice for this
-def _format_decimal_recursive(x, i, output, pts):
- if i < 0: # bottomed out with min_digit sized pieces
- if output or x.gt(NULLRBIGINT):
+def _format_decimal_recursive(x, i, output, pts, negative):
+ # bottomed out with min_digit sized pieces
+ # use str of ints
+ if i < 0:
+ # this checks whether any digit has been appended yet
+ # the extra char for negative rbigints is the '-'
+ if output.getlength() == negative:
+ if x.sign == 0:
+ pass
+ else:
+ s = str(x.toint())
+ output.append(s)
+ else:
s = str(x.toint())
- output.append("0"*(_FORMAT_DECIMAL_MINDIGITS - len(s)) + s) # note that this appends in inorder
+ output.append_multiple_char("0", _FORMAT_DECIMAL_MINDIGITS - len(s))
+ output.append(s)
else:
top,bot = x.divmod(pts[i]) # split the number
- _format_decimal_recursive(top,i-1, output, pts)
- _format_decimal_recursive(bot,i-1, output, pts)
+ _format_decimal_recursive(top, i-1, output, pts, negative)
+ _format_decimal_recursive(bot, i-1, output, pts, negative)
def _format_decimal_new(x, addL=False):
if x.sign == 0:
@@ -2213,17 +2224,20 @@
two = rbigint.fromint(2)
pts = [ten.pow(rbigint.fromint(_FORMAT_DECIMAL_MINDIGITS))]
+ stringsize = _FORMAT_DECIMAL_MINDIGITS
while pts[-1].lt(x):
pts.append(pts[-1].pow(two))
+ stringsize *= 2
pts.pop() # remove first 10**2**i greater than x
- output = []
- _format_decimal_recursive(x,len(pts)-1, output, pts)
- # strip leading zeros, we can probably do this more elegantly
- output = "".join(output)
- while len(output) > 1 and output[0] == "0":
- output = output[1:]
- return "-" * negative + output + "L" * addL
+ output = StringBuilder(stringsize)
+ if negative:
+ output.append('-')
+ _format_decimal_recursive(x,len(pts)-1, output, pts, negative)
+
+ if addL:
+ output.append('L')
+ return output.build()
def _bitwise(a, op, b): # '&', '|', '^'
More information about the pypy-commit
mailing list