I'm wondering what is the closest to a "SetList"; a list with all the amazing properties of both a list and a set.
For example, I'd want to index/subset it like a list, but make use of contains checking of a set, and making sure everything in it is unique.
Why not have both a set and a list occupying the same values (I know it is a terrible idea, there must be a way to contain the values once)? I figured it would be possible to implement all methods such that the list and set will always stay in sync.
I started with something like this:
class SetList():
    def __init__(self, x = None):
        if isinstance(x, list):
            self.l = []
            self.s = set()
            for y in x:
                if y not in self.s:
                    self.l.append(y)
                    self.s.add(y)
        elif isinstance(x, set):            
            self.l = list(x)
            self.s = x
        elif isinstance(x, SetList):
            self.l = SetList.l
            self.s = SetList.s
        elif x is None:
            self.l = []
            self.s = set()
        else:
            self.l = [x] 
            self.s = set(self.l)
    def append(self, a):
        if a not in self.s:
            self.l.append(a)
            self.s.add(a)
    def add(self, a):
        self.append(a)        
    def remove(self, r):
        if r in self.s:
            self.l.remove(r)
            self.s.remove(r)
    def pop(self, p = None):
        if p is not None:
            x = self.l.pop(p) 
        else:
            x = self.l.pop()
        self.s.remove(x)
        return x
    def __getitem__(self, i): 
        if isinstance(i, int):
            return self.l[i]
        else:
            return SetList(self.l[i])
    def __len__(self):
        return len(self.s)    
    def __repr__(self):
        return 'SetList({})'.format(self.l)
    def __add__(self, container):
        for x in container:
            if x not in self.s:
                self.add(x)
        return self        
    def __iter__(self):
        return self.l.__iter__()
    def __item__(self, x): 
        return self.l.__item__(x)
    def __and__(self, x):
        return self.__add__(x)
    def __eq__(self, x):
        try:
            return self.l == x.l
        except AttributeError: 
            return False
Here to see the goodness in action:
sl = SetList()
for x in [1,2,3,4,1,2,3]:
    sl.add(x)
>>> sl[1:2] + [1,3] != sl[1:2] & [3,1]
True
>>> sl[1:2] + [1,3] == sl[1:2] & [1,3]
True
Though I'm wondering if there are already such implementations out there?
