design a stack such that getMinimum should be O1
Master System Design with Codemia
Enhance your system design skills with over 120 practice problems, detailed solutions, and hands-on exercises.
When implementing a stack data structure, one of the frequently asked problems is to design it such that the getMinimum() function operates with a time complexity of . This means that the stack should be able to return the minimum element in constant time, irrespective of its current state. To achieve this, various approaches have been devised. This article delves into an effective method leveraging two parallel stacks to keep track of the minimum element, ensuring both efficiency and simplicity.
Understanding the Stack Data Structure
A stack is a Last-In-First-Out (LIFO) data structure, where elements are added or removed from the top of the stack. The primary operations associated with a stack include:
push(x): Add elementxto the top of the stack.pop(): Remove the element from the top of the stack and return it.top(): Return the element at the top of the stack without removing it.
The challenge lies in implementing getMinimum() that retrieves the minimum element without traversing the stack.
Dual Stack Approach
Concept
By maintaining two separate stacks, we can efficiently track the minimum element:
- Main Stack: This stack behaves like a regular stack, storing all the elements.
- Min Stack: This stack stores minimum values. The
minStackensures that each element in it is the minimum of all elements below it in themainStack.
Implementation
Here's how the push, pop, top, and getMinimum operations are implemented using two stacks:
- Push Operation:
- Push the element onto the
mainStack. - If the
minStackis empty or the new element is less than or equal to the current minimum (top of theminStack), push it onto theminStack.
- Pop Operation:
- Pop the element from the
mainStack. - If this element is equal to the top element of the
minStack, pop it from theminStackas well.
- Top Operation:
- Return the top element of the
mainStack.
- Get Minimum Operation:
- Return the top element of the
minStack.
Example Implementation
Here's a Python example:
Operation Analysis
The following table summarizes the operations and their respective time complexities:
| Operation | Description | Time Complexity |
push(x) | Push x to both mainStack and minStack if needed. | |
pop() | Pop from mainStack and minStack if top elements match. | |
top() | Retrieve the top element from mainStack. | |
getMinimum() | Retrieve the minimum element from minStack. |
Space Complexity
The space complexity of this approach is , where is the number of elements in the stack. This is because, in the worst-case scenario, each element in the mainStack could also reside in the minStack if the sequence of inserted numbers is monotonically decreasing.
Advantages and Considerations
- Efficiency: The dual stack method is efficient, with time complexity for all fundamental operations.
- Simplicity: Implementing two stacks is straightforward and easy to understand.
- Space Trade-off: While powerful, this method uses extra space for the
minStack. In applications where memory is a constraint, other advanced methods like using a single stack with auxiliary data might be preferred.
Advanced Alternatives
While the dual stack method is optimal for most use cases, other methods such as augmenting the stack with differential data or adopting a linked list approach can also be considered for special use cases.
Overall, using a dual stack approach simplifies the problem of achieving time complexity for getMinimum(), offering a neat balance between computational and spatial efficiency. This structuring finds its use in numerous real-world applications where quick access to minimum values in a dynamic data set is crucial, such as financial systems handling real-time data and algorithmic trading platforms.

