how can I subclass a string (str)?

Jason R. Coombs jaraco at spamblocker.sandia.gov
Thu Aug 15 19:33:38 CEST 2002


Thanks (to all) for the suggestions.  I decided that I didn't want to have a
mutable string, but I wanted to be able to generate a binary string from a
hex string, so here's what I came up with:

class Binary( str ):
 def __repr__( self ):
  return '0x' + self.ASCII

 def _GetASCIIRepresentation( self ):
  return string.join( map( lambda n: '%02x' % n, map( ord, self ) ), '' )

 ASCII = property( _GetASCIIRepresentation )

 def CreateFromASCIIRepresentation( s ):
  isHex = re.match( '(0x)?([0-9a-fA-F]*)$', s )
  if not isHex:
   raise ValueError, 'String is not hex characters'
  s = isHex.group(2)
  if not len( s ) % 2 == 0:
   raise ValueError, 'String must be of even length'
  even = range( 0, len( s ), 2 )
  odd = range( 1, len( s ), 2 )
  even = map( s.__getitem__, even )
  odd = map( s.__getitem__, odd )
  bytes = map( operator.add, even, odd )
  toBin = lambda byteStr: chr( long( byteStr, 16 ) )
  return Binary( string.join( map( toBin, bytes ), '' ) )

 CreateFromASCIIRepresentation = staticmethod(
CreateFromASCIIRepresentation )


Notice in _GetASCIIRepresentation, I use the lambda n: '%02x' % n function
instead of hex().  This is because hex prepends a '0x' to each string.

Thanks for the suggestions.

Jason

"Loic fejoz" <loic at fejoz.net> wrote in message
news:ajd3bq$8if$1 at sunnews.cern.ch...
> Loic fejoz <loic at fejoz.net> wrote:
> > Jason R. Coombs <jaraco at spamblocker.sandia.gov> wrote:
> >> [...]
> >> BinaryString( '\x33\x22\xAB' ).HexRepr() == '0x3322ab'
> >> and
> >> repr( BinaryString().SetHexRepr( '0x3322AB' ) ) == '\x33\x22\xab'  #
> >> 0x prefix is optional
> >> [..]
> >> Perhaps my approach to this problem is all wrong.  Are there any
> >> suggestions for creating an elegant solution to the problem
> >> described?
> >>
> >> Thanks much,
> >> Jason
> >
> > what about the attach code ?
> > cheers,
>
> seems better to copy it...
>
> import UserString
> import string
> import re
>
> class BinaryString(UserString.UserString):
>     def __repr__(self):
>         return self.hexRepr()
>
>     def __str__(self):
>         return self.hexRepr()
>
>     def hexRepr(self,groupBy = -1):
>         ch = '0x'
>         i = 0
>         for char in self.data:
>             ch = ch + hex(ord(char))[2:] #remove '0x'
>             i = i + 1
>             if i == groupBy:
>                 ch = ch + ' '
>                 i = 0
>         return ch
>
>     def setHexRepr(self,hexRepr):
>         ch = ''
>         if hexRepr[:2] == '0x':
>             hexRepr = hexRepr[2:]
>         hexRepr = string.replace(hexRepr,' ','')
>         tokens = re.split('([0-9a-fA-F][0-9a-fA-F])',hexRepr)
>         for tok in tokens:
>             if tok:
>                 ch = ch + chr(int(tok,16))
>         self.data = ch
>
>     def getString(self):
>         return self.data
>
>
> if __name__=="__main__":
>     ch = BinaryString('ab\x10\xCF\xFFc')
>     print ch
>     print ch.hexRepr(2)
>     print ch.getString()
>     ch1 = BinaryString('')
>     print ch1
>     ch1.setHexRepr('0xFFEEDDCCBBAA10')
>     print ch1
>     ch2 = BinaryString('')
>     ch2.setHexRepr('0x6465 3132')
>     print ch2
>     print ch2.getString()
>
> --
> Loïc
>
>





More information about the Python-list mailing list