Data Structures / Stack

Valid Parentheses

Easy
Solve this question on LeetCode

Given a string s containing just the characters '(', ')', '{', '}', '[' and ']', determine if the input string is valid.

An input string is valid if: (1) Open brackets must be closed by the same type of brackets. (2) Open brackets must be closed in the correct order.

Example

Input: s = "()"
Output: true
Input: s = "()[]{}"
Output: true
Input: s = "(]""
Output: false
Input: s = "([)]"
Output: false
Explanation: The brackets are closed, but not in the correct order.

Explanation

The most efficient approach to solve this problem is using a stack. The key insight is that we need to match opening brackets with their corresponding closing brackets in the correct order (Last In, First Out).

We iterate through the string and for each character:

  1. If it's an opening bracket ('(', '{', '['), push it onto the stack
  2. If it's a closing bracket (')', '}', ']'):
    • Check if the stack is empty (if so, return false — no matching opener)
    • Pop the top element and check if it matches the current closing bracket
    • If it doesn't match, return false
  3. After processing all characters, return true only if the stack is empty

This approach works because stacks naturally handle the LIFO (Last In, First Out) nature of nested structures — the most recent opening bracket must be closed first.

Idea Map

Start

Create empty stack = []

For each char in s

If char is '(' '{' '['
→ Push to stack

If char is ')' '}' ']'
→ If stack.empty() or top doesn't match
   Return false
→ Else: pop()

Return stack.empty()

End

Complexity Analysis

Time Complexity

O(n) - We traverse the string once, and each stack operation (push/pop) is O(1).

Space Complexity

O(n) - In the worst case (all opening brackets), we store all n characters in the stack.

Code


def isValid(s: str) -> bool:
Initializes the function `isValid` which takes a string `s` containing brackets and returns a boolean indicating if the string is valid.
stack = []
Creates an empty list to use as our stack data structure for tracking opening brackets.
mapping = {')': '(', '}': '{', ']': '['}
Creates a dictionary mapping each closing bracket to its corresponding opening bracket for easy matching.
for char in s:
Loops through each character in the input string one by one.
if char in mapping:
Checks if the current character is a closing bracket (exists as a key in mapping).
if not stack or stack.pop() != mapping[char]:
If stack is empty OR the popped opening bracket doesn't match this closing bracket, the string is invalid.
return False
Return False immediately if we find a mismatch or extra closing bracket.
else:
If the character is not a closing bracket, it must be an opening bracket.
stack.append(char)
Push the opening bracket onto the stack to be matched later with its closing bracket.
return len(stack) == 0
Return True only if stack is empty (all opening brackets were matched).

public boolean isValid(String s) {
Initializes the function `isValid` which takes a string `s` and returns a boolean indicating validity.
Deque<Character> stack = new ArrayDeque<>();
Creates a Deque (double-ended queue) to use as a stack for tracking opening brackets.
for (char c : s.toCharArray()) {
Loops through each character in the input string after converting it to a char array.
if (c == '(') {
Checks if the current character is an opening parenthesis.
stack.push(')');
Push the corresponding closing bracket onto the stack (clever matching trick!).
} else if (c == '{') {
Checks if the current character is an opening curly brace.
stack.push('}');
Push the corresponding closing curly brace onto the stack.
} else if (c == '[') {
Checks if the current character is an opening square bracket.
stack.push(']');
Push the corresponding closing square bracket onto the stack.
} else if (stack.isEmpty() || stack.pop() != c) {
If it's a closing bracket: if stack is empty OR popped element doesn't match, string is invalid.
return false;
Return False immediately if we find a mismatch or extra closing bracket.
}
End of the if-else chain.
}
End of the for loop.
return stack.isEmpty();
Return True only if stack is empty (all opening brackets were matched).
}
End of the function.

bool isValid(string s) {
Initializes the function `isValid` which takes a string `s` and returns a boolean indicating validity.
stack<char> st;
Creates a stack of characters to track opening brackets.
for (char c : s) {
Range-based for loop to iterate through each character in the string.
if (c == '(' || c == '{' || c == '[') {
Checks if the current character is any type of opening bracket.
st.push(c);
Push the opening bracket onto the stack for later matching.
} else {
If it's not an opening bracket, it must be a closing bracket.
if (st.empty()) return false;
If stack is empty when we encounter a closing bracket, there's no matching opener — invalid!
char top = st.top(); st.pop();
Get the top element from stack and remove it (we need to check if it matches).
if ((c == ')' && top != '(') ||
Check if closing parenthesis doesn't match opening parenthesis.
(c == '}' && top != '{') ||
Check if closing curly brace doesn't match opening curly brace.
(c == ']' && top != '[')) {
Check if closing square bracket doesn't match opening square bracket.
return false;
If any bracket type doesn't match, return False immediately.
}
End of the mismatch check if statement.
}
End of the if-else block.
}
End of the for loop.
return st.empty();
Return True only if stack is empty (all brackets were properly matched).
}
End of the function.

Edge Cases & Common Mistakes

⚠️

Empty string edge case

An empty string is technically valid (no unmatched brackets), so ensure your code returns true for this case.

💡

Odd-length strings

Any string with an odd number of characters is automatically invalid. You can add an early check for this optimization.

Check stack before popping

Always check if the stack is empty before calling pop() or peek() to avoid errors on extra closing brackets.

What is a Stack?

A stack is a linear data structure that follows the Last In, First Out (LIFO) principle. Think of it like a stack of plates — you can only add (push) or remove (pop) from the top. This makes stacks perfect for matching nested structures like parentheses!

Learn more about stacks →
layers

Disclaimer: This problem is for educational purposes. Practice the 'Valid Parentheses' problem on LeetCode.