Stacks
A Stack is a linear data structure that follows the LIFO (Last In, First Out) principle. Think of a stack of plates — you can only add or remove plates from the top.
Core Operations
All stack operations are O(1) — constant time!
| Operation | Description | Time |
|---|---|---|
| push(x) | Add element to top | O(1) |
| pop() | Remove and return top element | O(1) |
| peek() / top() | View top element without removing | O(1) |
| isEmpty() | Check if stack is empty | O(1) |
| size() | Get number of elements | O(1) |
Implementation
Using an Array
class Stack {
constructor() {
this.items = [];
}
push(element) {
this.items.push(element);
}
pop() {
if (this.isEmpty()) {
return "Stack is empty";
}
return this.items.pop();
}
peek() {
if (this.isEmpty()) {
return "Stack is empty";
}
return this.items[this.items.length - 1];
}
isEmpty() {
return this.items.length === 0;
}
size() {
return this.items.length;
}
}
// Usage
const stack = new Stack();
stack.push(10);
stack.push(25);
stack.push(42);
console.log(stack.peek()); // 42
console.log(stack.pop()); // 42
console.log(stack.peek()); // 25
Python Implementation
class Stack:
def __init__(self):
self.items = []
def push(self, item):
self.items.append(item)
def pop(self):
if not self.is_empty():
return self.items.pop()
return None
def peek(self):
if not self.is_empty():
return self.items[-1]
return None
def is_empty(self):
return len(self.items) == 0
def size(self):
return len(self.items)
Classic Problem: Balanced Parentheses
One of the most common stack problems — checking if brackets are balanced:
function isBalanced(str) {
const stack = [];
const pairs = { ')': '(', '}': '{', ']': '[' };
for (const char of str) {
if ('({['.includes(char)) {
stack.push(char);
} else if (')}]'.includes(char)) {
if (stack.pop() !== pairs[char]) {
return false;
}
}
}
return stack.length === 0;
}
console.log(isBalanced("({[]})")); // true
console.log(isBalanced("({[})")); // false
console.log(isBalanced("((")); // false
Real-World Applications
- Undo/Redo — Each action is pushed; Ctrl+Z pops the last action
- Browser Back Button — Pages are stacked; back pops the current page
- Function Call Stack — Each function call pushes a frame; return pops it
- Expression Evaluation — Convert infix to postfix, evaluate postfix
- Backtracking — DFS, maze solving, generating permutations
The Call Stack
Every programming language uses a stack for function calls:
function first() {
console.log("First");
second();
console.log("First done");
}
function second() {
console.log("Second");
third();
console.log("Second done");
}
function third() {
console.log("Third");
}
first();
// Output: First, Second, Third, Second done, First done
The call stack grows with each function call and shrinks as functions return.
Stack vs Array
| Aspect | Stack | Array |
|---|---|---|
| Access | Only top element | Any element by index |
| Insert | Only at top (push) | Anywhere |
| Delete | Only from top (pop) | Anywhere |
| Use case | LIFO scenarios | Random access needed |
What's Next?
Next, we'll explore Queues — the opposite of stacks, following FIFO (First In, First Out), perfect for task scheduling and breadth-first search.