Incrementing a string
Andrew Dalke
adalke at mindspring.com
Thu Sep 16 01:49:36 EDT 2004
Phil Frost wrote:
> import string
>
> class LabelCounter(object):
> digits = string.lowercase
....
> # define other operators as needed; it's a shame this can't inherit from
> # int and get these for free. It can't do this because all of int's
> # operators return ints, not LabelCounters.
Try this instead. As usual with clever solutions, you
probably shouldn't use this in real code.
import string
def fixup(klass):
for name, meth in inspect.getmembers(klass):
# Find all the methods except for a few special ones
# we know won't return integers
if (callable(meth) and name not in
["__class__", "__new__", "__init__", "__str__", "__repr__"]):
# Need to make a wrapper function (g) for each of these methods.
# The wrapper function needs to know the original method, which
# is stored in the newly created scope (f).
def f(meth = meth):
def g(self, *args, **kwargs):
retval = meth(self, *args, **kwargs)
if isinstance(retval, int):
return LabelCounter(retval)
return retval
return g
g = f()
setattr(klass, name, g) # replace with the wrapped version
class LabelCounter(int):
digits = string.ascii_lowercase
def __str__(self):
letters = []
i = int(self)
while i:
d, m = divmod(i, len(self.digits))
letters.append(self.digits[m])
i = d
return "".join(letters[::-1]) or self.digits[0]
__repr__ = __str__
Here it is in use.
>>> a = LabelCounter(4)
>>> print a
e
>>> print a+1
f
>>> print a+10
o
>>> print (a+10)/2
h
>>> print a
e
>>> print a/2
c
>>> print a/3
b
>>> print a/30
a
>>> print a**4
jw
>>>
> You can set 'digits' to any sequence at all. Set it to '01' to get
> output in binary, or to ['01','23','45','67','89'] to get base 5 in a
> very confusing notation *g*
I set it to ascii_lowercase since string.lowercase is locale
dependent.
>>> import string, locale
>>> string.lowercase
'abcdefghijklmnopqrstuvwxyz'
>>> locale.setlocale(locale.LC_ALL, "de_DE")
'de_DE'
>>> string.lowercase
'abcdefghijklmnopqrstuvwxyz\xaa\xb5\xba\xdf\xe0\xe1\xe2\xe3\xe4\xe5\xe6\xe7\xe8\xe9\xea\xeb\xec\xed\xee\xef\xf0\xf1\xf2\xf3\xf4\xf5\xf6\xf8\xf9\xfa\xfb\xfc\xfd\xfe\xff'
>>>
OTOH, that might be what you wanted ...
Andrew
dalke at dalkescientific.com
More information about the Python-list
mailing list