Push(10), Push(20), Pop(), Push(30), Push(40), Pop()
package main import "fmt" type Stack struct { arr []int top int } func NewStack() *Stack { return &Stack{arr: make([]int, 2), top: -1} } func (s *Stack) Push(val int) { if s.top+1 == len(s.arr) { newArr := make([]int, len(s.arr)*2) copy(newArr, s.arr) s.arr = newArr } s.top++ s.arr[s.top] = val } func (s *Stack) Pop() int { if s.top == -1 { return -1 } val := s.arr[s.top] s.top-- return val } func (s *Stack) Print() { for i := 0; i <= s.top; i++ { fmt.Print(s.arr[i]) if i != s.top { fmt.Print(" -> ") } } fmt.Println(" -> null") } func main() { stack := NewStack() stack.Push(10) stack.Push(20) stack.Pop() stack.Push(30) stack.Push(40) stack.Pop() stack.Print() }
After pushing 10 and 20, stack is 10 -> 20 -> null.
Pop removes 20, stack is 10 -> null.
Push 30 and 40, stack becomes 10 -> 30 -> 40 -> null.
Pop removes 40, stack is 10 -> 30 -> null.
Push 1, Push 2, Push 3, Push 4, Push 5 on a stack initialized with capacity 2.
package main import "fmt" type Stack struct { arr []int top int } func NewStack() *Stack { return &Stack{arr: make([]int, 2), top: -1} } func (s *Stack) Push(val int) { if s.top+1 == len(s.arr) { newArr := make([]int, len(s.arr)*2) copy(newArr, s.arr) s.arr = newArr } s.top++ s.arr[s.top] = val } func main() { stack := NewStack() stack.Push(1) stack.Push(2) stack.Push(3) stack.Push(4) stack.Push(5) fmt.Println(len(stack.arr)) }
Initial capacity is 2.
Push 1 and 2 fills it.
Push 3 triggers resize to 4.
Push 4 fills capacity 4.
Push 5 triggers resize to 8.
Final capacity is 8.
func (s *Stack) Pop() int { val := s.arr[s.top] s.top-- return val }
If the stack is empty, s.top is -1.
Accessing s.arr[-1] causes runtime panic: index out of range.
Resizable arrays grow automatically when full, avoiding overflow.
Fixed arrays have a fixed size and can overflow.
Memory use and pop speed depend on implementation.
Top pointer is still needed.
Push(5), Push(10), Push(15), Pop(), Push(20), Pop(), Pop(), Push(25), Push(30), Push(35), Pop()
package main import "fmt" type Stack struct { arr []int top int } func NewStack() *Stack { return &Stack{arr: make([]int, 2), top: -1} } func (s *Stack) Push(val int) { if s.top+1 == len(s.arr) { newArr := make([]int, len(s.arr)*2) copy(newArr, s.arr) s.arr = newArr } s.top++ s.arr[s.top] = val } func (s *Stack) Pop() int { if s.top == -1 { return -1 } val := s.arr[s.top] s.top-- return val } func (s *Stack) Print() { for i := 0; i <= s.top; i++ { fmt.Print(s.arr[i]) if i != s.top { fmt.Print(" -> ") } } fmt.Println(" -> null") } func main() { stack := NewStack() stack.Push(5) stack.Push(10) stack.Push(15) stack.Pop() stack.Push(20) stack.Pop() stack.Pop() stack.Push(25) stack.Push(30) stack.Push(35) stack.Pop() stack.Print() }
Operations:
Push 5: stack 5
Push 10: 5 -> 10
Push 15: 5 -> 10 -> 15
Pop: removes 15 -> 5 -> 10
Push 20: 5 -> 10 -> 20
Pop: removes 20 -> 5 -> 10
Pop: removes 10 -> 5
Push 25: 5 -> 25
Push 30: 5 -> 25 -> 30
Push 35: 5 -> 25 -> 30 -> 35
Pop: removes 35 -> 5 -> 25 -> 30
