slice-alias (was Re: New statement proposal for Python)
Alex Martelli
aleaxit at yahoo.com
Sat Jun 16 04:44:37 EDT 2001
"Andrew Henshaw" <ahenshaw at apower dot com> wrote in message
news:tiljnnden7bc80 at corp.supernews.com...
...
> For instance, one can alias (e.g. "lastName") a slice [16:32] of an Occam
> array of bytes "byteArray" with:
>
> lastName IS [byteArray FROM 16 FOR 16]:
>
> and then use lastName as a new array name. Then the first byte can be
> referrenced with:
>
> lastName[0] := 'a'
>
> This, of course, will change the 17th byte in byteArray to 'a'.
...
> This would be nice on Python as well, particularly since naming a list
slice
> actually creates a copy (perhaps I've missed some capability here).
Takes some work, and is untested, but...:
import types,sys
class ListSlice:
def __init__(self, alist, start, stop=None):
self.alist=alist
self.start=start
self.stop=stop
def __stopper(self):
if self.stop is None: return len(self.alist)
else: return self.stop
def __normindex(self, index, aslice=0):
if index<0:
result = self.__stopper()+index
else:
try: result = self.start+index
except OverflowError:
if aslice==2: return self.__stopper()
raise
if self.start<=result<self.__stopper():
return result
else:
if aslice==1: return self.start
elif aslice==2: return self.__stopper()
else: raise IndexError, result
def __sliceit(self, index):
if index.step is not None:
raise TypeError, "sequence index must be integer"
newstart = self.__normindex(index.start,1)
newstop = self.__normindex(index.stop,2)
return newstart, newstop
def __len__(self):
return max(0, self.__stopper()-self.start)
def __getitem__(self, index):
if type(index)==types.SliceType:
newstart, newstop = self.__sliceit(index)
return self.alist[newstart:newstop]
else:
return self.alist[self.__normindex(index)]
def __setitem__(self, index, value):
if type(index)==types.SliceType:
newstart, newstop = self.__sliceit(index)
self.alist[newstart:newstop] = value
else:
self.alist[self.__normindex(index)] = value
>> base = list("prolegomena")
>> slic=ListSlice(base,2,6)
>>> ''.join(slic)
'oleg'
>>> ''.join(base)
'prolegomena'
>>> slic[:3]
['o', 'l', 'e']
>>> slic[2:]
['e', 'g']
>>> slic[1:4]
['l', 'e', 'g']
>>> slic[1:3]
['l', 'e']
>>> slic[1:3]=list("plop")
>>> ''.join(base)
'proplopgomena'
>>> ''.join(slic)
'oplo'
>>>
As you see, it itsn't perfect -- the slice should no doubt
adjust its length in some more circumstances, the better
to mimic a built-in sequence, specifically when it's subject
to slice-assignment. But I hope it can get you started.
Alex
More information about the Python-list
mailing list