Пример #1
0
class RootishArrayStack(BaseList):
    def __init__(self, iterable=[]):
        self._initialize()
        self.add_all(iterable)

    def _initialize(self):
        self.n = 0
        self.blocks = ArrayStack()

    def _i2b(self, i):
        return int(ceil((-3.0 + sqrt(9 + 8 * i)) / 2.0))

    def grow(self):
        self.blocks.append(new_array(self.blocks.size() + 1))

    def shrink(self):
        r = self.blocks.size()
        while r > 0 and (r - 2) * (r - 1) / 2 >= self.n:
            self.blocks.remove(self.blocks.size() - 1)
            r -= 1

    def get(self, i):
        if i < 0 or i > self.n - 1: raise IndexError()
        b = self._i2b(i)
        j = i - b * (b + 1) / 2
        return self.blocks.get(b)[j]

    def set(self, i, x):
        if i < 0 or i > self.n - 1: raise IndexError()
        b = self._i2b(i)
        j = i - b * (b + 1) / 2
        y = self.blocks.get(b)[j]
        self.blocks.get(b)[j] = x
        return y

    def add(self, i, x):
        if i < 0 or i > self.n: raise IndexError()
        r = self.blocks.size()
        if r * (r + 1) / 2 < self.n + 1: self.grow()
        self.n += 1
        for j in range(self.n - 1, i, -1):
            self.set(j, self.get(j - 1))
        self.set(i, x)

    def remove(self, i):
        if i < 0 or i > self.n - 1: raise IndexError()
        x = self.get(i)
        for j in range(i, self.n - 1):
            self.set(j, self.get(j + 1))
        self.n -= 1
        r = self.blocks.size()
        if (r - 2) * (r - 1) / 2 >= self.n: self.shrink()
        return x

    def clear(self):
        self.blocks.clear()
        self.n = 0
Пример #2
0
class RootishArrayStack(BaseList):
    def __init__(self, iterable=[]):
        self._initialize()
        self.add_all(iterable)
        
    def _initialize(self):
        self.n = 0
        self.blocks = ArrayStack()

    def _i2b(self, i):
        return int(ceil((-3.0 + sqrt(9 + 8*i)) / 2.0))
    
    def grow(self):
        self.blocks.append(new_array(self.blocks.size()+1))
    
    def shrink(self):
        r = self.blocks.size()
        while r > 0 and (r-2)*(r-1)/2 >= self.n:
            self.blocks.remove(self.blocks.size()-1)
            r -= 1
    
    def get(self, i):
        if i < 0 or i > self.n - 1: raise IndexError()
        b = self._i2b(i)
        j = i - b*(b+1)/2
        return self.blocks.get(b)[j]

    def set(self, i, x):
        if i < 0 or i > self.n - 1: raise IndexError()
        b = self._i2b(i)
        j = i - b*(b+1)/2
        y = self.blocks.get(b)[j]
        self.blocks.get(b)[j] = x
        return y
    
    def add(self, i, x):
        if i < 0 or i > self.n: raise IndexError()
        r = self.blocks.size()
        if r*(r+1)/2 < self.n + 1: self.grow()
        self.n += 1
        for j in range(self.n-1, i, -1):
            self.set(j, self.get(j-1))
        self.set(i, x)
    
    def remove(self, i):
        if i < 0 or i > self.n - 1: raise IndexError()
        x = self.get(i)
        for j in range(i, self.n-1):
            self.set(j, self.get(j+1))
        self.n -= 1
        r = self.blocks.size()
        if (r-2)*(r-1)/2 >= self.n: self.shrink()
        return x

    def clear(self):
        self.blocks.clear()
        n = 0
Пример #3
0
class DualArrayDeque(BaseList):
    def __init__(self, iterable=[]):
        self._initialize()
        self.add_all(iterable)

    def _initialize(self):
        self.front = ArrayStack()
        self.back = ArrayStack()

    def get(self, i):
        if i < self.front.size():
            return self.front.get(self.front.size() - i - 1)
        else:
            return self.back.get(i - self.front.size())

    def set(self, i, x):
        if i < self.front.size():
            return self.front.set(self.front.size() - i - 1, x)
        else:
            return self.back.set(i - self.front.size(), x)

    def add(self, i, x):
        if i < self.front.size():
            self.front.add(self.front.size() - i, x)
        else:
            self.back.add(i - self.front.size(), x)
        self._balance()

    def remove(self, i):
        if i < self.front.size():
            x = self.front.remove(self.front.size() - i - 1)
        else:
            x = self.back.remove(i - self.front.size())
        self._balance()
        return x

    def _balance(self):
        n = self.size()
        mid = n // 2
        if 3 * self.front.size() < self.back.size(
        ) or 3 * self.back.size() < self.front.size():
            f = ArrayStack()
            for i in range(mid):
                f.add(i, self.get(mid - i - 1))
            b = ArrayStack()
            for i in range(n - mid):
                b.add(i, self.get(mid + i))
            self.front = f
            self.back = b

    def clear(self):
        self.front.clear()
        self.back.clear()

    def size(self):
        return self.front.size() + self.back.size()
Пример #4
0
class DualArrayDeque(BaseList):
    def __init__(self, iterable=[]):
        self._initialize()
        self.add_all(iterable)

    def _initialize(self):
        self.front = ArrayStack()
        self.back = ArrayStack()

    def get(self, i):
        if i < self.front.size():
            return self.front.get(self.front.size() - i - 1)
        else:
            return self.back.get(i - self.front.size())

    def set(self, i, x):
        if i < self.front.size():
            return self.front.set(self.front.size() - i - 1, x)
        else:
            return self.back.set(i - self.front.size(), x)

    def add(self, i, x):
        if i < self.front.size():
            self.front.add(self.front.size() - i, x)
        else:
            self.back.add(i - self.front.size(), x)
        self._balance()

    def remove(self, i):
        if i < self.front.size():
            x = self.front.remove(self.front.size() - i - 1)
        else:
            x = self.back.remove(i - self.front.size())
        self._balance()
        return x

    def _balance(self):
        n = self.size()
        mid = n // 2
        if 3 * self.front.size() < self.back.size() or 3 * self.back.size() < self.front.size():
            f = ArrayStack()
            for i in range(mid):
                f.add(i, self.get(mid - i - 1))
            b = ArrayStack()
            for i in range(n - mid):
                b.add(i, self.get(mid + i))
            self.front = f
            self.back = b

    def clear(self):
        self.front.clear()
        self.back.clear()

    def size(self):
        return self.front.size() + self.back.size()