Implementing Stack with Python

前端 未结 12 1094
长发绾君心
长发绾君心 2021-01-17 16:16

I am trying to implement a simple stack with Python using arrays. I was wondering if someone could let me know what\'s wrong with my code.

class myStack:
            


        
相关标签:
12条回答
  • 2021-01-17 16:45
    class Stack:
       s =[]
    
       def push(self, num):
           self.s.append(num)
    
       def pop(self):
           if len(self.s) == 0: # erro if you pop an empty list
               return -1
           self.s.remove(self.s[-1])
    
       def isEmpty(self):
           if len(self.s) == 0:
               return True
           else:
               return False
    
       def display(self): # this is to display how a stack actually looks like
           if self.isEmpty():
               print("Stack is Empty")
        
           for i in range(len(self.s)-1,-1,-1): # I haven't used reversed() since it will be obv
               print(self.s[i])
    
    
    obj = Stack()
    obj.push(3)
    print(obj.isEmpty())
    obj.push(4)
    obj.display()
    print("----")
    obj.pop()
    obj.display()
    
    0 讨论(0)
  • 2021-01-17 16:48

    Assigning to self won't turn your object into a list (and if it did, the object wouldn't have all your stack methods any more). Assigning to self just changes a local variable. Instead, set an attribute:

    def __init__(self):
        self.stack = []
    

    and use the attribute instead of just a bare self:

    def push(self, item):
        self.stack.append(item)
    

    Also, if you want a stack, you want pop() rather than pop(0). pop(0) would turn your data structure into a(n inefficient) queue.

    0 讨论(0)
  • 2021-01-17 16:53

    A stack is a container (linear collection) in which dynamic set operations are carried out as per the last-in first-out (LIFO) principle. There is only one pointer - top, which is used to perform these operations

    CLRS implementation of stack using array:

    class Stack:
        """
        Last in first out (LIFO) stack implemented using array.
        """
        def __init__(self, capacity=4):
            """
            Initialize an empty stack array with default capacity of 4.
            """
            self.data = [None] * capacity
            self.capacity = capacity
            self.top  = -1
    
        def is_empty(self):
            """
            Return true if the size of stack is zero.
            """
            if self.top == -1:
                return True
            return False
    
        def push(self, element):
            """
            Add element to the top.
            """
            self.top += 1
            if self.top >= self.capacity:
                raise IndexError('Stack overflow!')
            else:
                self.data[self.top] = element
    
        def pop(self):
            """
            Return and remove element from the top.
            """
            if self.is_empty():
                raise Exception('Stack underflow!')
            else:
                stack_top = self.data[self.top]
                self.top -= 1
                return stack_top
    
        def peek(self):
            """
            Return element at the top.
            """
            if self.is_empty():
                raise Exception('Stack is empty.')
                return None
            return self.data[self.top]
    
        def size(self):
            """
            Return the number of items present.
            """
            return self.top + 1
    
    

    Testing the implemetation:

    def main():
        """
        Sanity test
        """
        stack = Stack()
    
        print('Size of the stack is:', stack.size())
        stack.push(3)
        print('Element at the top of the stack is: ', stack.peek())
        stack.push(901)
        print('Element at the top of the stack is: ', stack.peek())
        stack.push(43)
        print('Element at the top of the stack is: ', stack.peek())
        print('Size of the stack is:', stack.size())
        stack.push(89)
        print('Element at the top of the stack is: ', stack.peek())
        print('Size of the stack is:', stack.size())
        #stack.push(9)    # Raises IndexError
        stack.pop()
        print('Size of the stack is:', stack.size())
        stack.pop()
        print('Size of the stack is:', stack.size())
        stack.pop()
        print('Size of the stack is:', stack.size())
        print('Element at the top of the stack is: ', stack.peek())
        stack.pop()
        #print('Element at the top of the stack is: ', stack.peek())    # Raises empty stack exception
    
    if __name__ == '__main__':
        main()
    
    0 讨论(0)
  • 2021-01-17 16:58

    I left a comment with the link to http://docs.python.org/2/tutorial/datastructures.html#using-lists-as-stacks, but if you want to have a custom type that gives you push, pop, is_empty, and size convenience methods, I'd just subclass list.

    class Stack(list):
        def push(self, item):
            self.append(item)
        def size(self):
            return len(self)
        def is_empty(self):
            return not self
    

    However, as I said in the comments, I'd probably just stick with a straight list here, as all you are really doing is aliasing existing methods, which usually only serves to make your code harder to use in the long run, as it requires people using it to learn your aliased interface on top of the original.

    0 讨论(0)
  • 2021-01-17 16:58

    Your problem is that you're popping from the beginning of the list, when you should be popping from the end of the list. A stack is a Last-In First-Out data structure, meaning that when you pop something from it, that something will be whatever you pushed on last. Take a look at your push function - it appends an item to the list. That means that it goes at the end of the list. When you call .pop(0), however, you're removing the first item in the list, not the one you last appended. Removing the 0 from .pop(0) should solve your problem.

    0 讨论(0)
  • 2021-01-17 16:59

    I would like to share my version of the stack implementation that inherits Python List. I believe iteration on a stack should be happening in LIFO order. Additionally, an iteration on pop-all() should be provided to iterate while poping all elements. I have also added stack.clear() to empty a stack (like we have in deque.clear() in collections module). I have also override __repr__ for debugging purpose:

    class Stack(list):
    
        def push(self, item):
            self.append(item)
    
        def top(self):
            return self[-1]
    
        def size(self):
            return len(self)
    
        def isempty(self):
            return self.size() == 0
    
        def __iter__(self):
            """ iter in lifo """
            return super(Stack, self).__reversed__()
    
        def __reversed__(self):
            return super(Stack, self).__iter__()
    
        def popall(self):
            try:
                while True:
                    yield self.pop()
            except IndexError:
                pass
    
        def clear(self):
            del self[:]
    
        def __repr__(self):
            if not self:
                return '%s()' % self.__class__.__name__
            return '%s(%s)' % (self.__class__.__name__, super(Stack, self).__repr__())
    

    Here is how you can use it:

    stack = Stack(range(5))
    print "stack: ", stack  # stack:  Stack([0, 1, 2, 3, 4])
    
    print "stack.pop() => ", stack.pop() # stack.pop() =>  4
    print "stack.push(20) " # stack.push(20) 
    stack.push(20)
    for item in stack:
        print item  # prints 20, 3, 2... in newline
    print "stack: ", stack # stack:  Stack([0, 1, 2, 3, 20])
    print "stack pop all..."
    for item in stack.popall(): # side effect to clear stack
        print item
    print "stack: ", stack # stack:  Stack()
    

    Primary, I implemented it to use to solve a programming problem next greater element.

    0 讨论(0)
提交回复
热议问题