Given an array of string tokens representing a valid arithmetic expression in Reverse Polish Notation (postfix notation), evaluate it and return the integer result. Operators are +, -, *, /. Division truncates toward zero.
1 ≤ tokens.length ≤ 1000[-100, 100]Normal math uses parentheses to express order of operations: (2 + 1) * 3. Reverse Polish Notation removes the parentheses by placing the operator after its operands: 2 1 + 3 *. The order of the tokens encodes the order of evaluation.
A stack fits this perfectly. When you see a number, hold it. When you see an operator, the two most recent numbers are its operands — pop them, compute, push the result back. At the end, one number remains: the answer.
Repeatedly scan the token list. When you find an operator, take the two numbers before it, compute the result, and collapse those three tokens into one. Restart the scan until only one token remains.
def evalRPN(tokens):
while len(tokens) > 1:
for i in range(len(tokens)):
if tokens[i] in "+-*/":
a, b = int(tokens[i-2]), int(tokens[i-1])
result = a + b if tokens[i] == '+' else \
a - b if tokens[i] == '-' else \
a * b if tokens[i] == '*' else int(a / b)
tokens = tokens[:i-2] + [str(result)] + tokens[i+1:]
break
return int(tokens[0])Each scan is O(n) and you may do up to O(n) scans, giving O(n²) overall. The stack solution is a single pass.
One pass through tokens. Numbers push; operators pop two, compute, push one.
def evalRPN(tokens):
stack = []
for c in tokens:
if c not in "+-*/":
stack.append(int(c))
elif c == "+":
stack.append(stack.pop() + stack.pop())
elif c == "-":
a, b = stack.pop(), stack.pop()
stack.append(b - a)
elif c == "*":
stack.append(stack.pop() * stack.pop())
else:
a, b = stack.pop(), stack.pop()
stack.append(int(b / a)) # truncate toward zero
return stack[0]| Approach | Time | Space |
|---|---|---|
| Brute Force (rescan) | O(n²) | O(n) |
| Stack | O(n) | O(n) |
Any time you need to evaluate a sequence where earlier values are consumed by later operators, a stack is the tool. This is the basis of how virtually every programming language evaluates expressions internally.
tokens.length ≤ 1000 — O(n²) would work on size, but a clean O(n) stack is expected.-7/2 = -3, not -4.The first pop gives the right operand; the second pop gives the left. For commutative operators (+, *) order doesn't matter. For - and / it does.
# tokens = ["5", "3", "-"] → should be 5 - 3 = 2 a = stack.pop() # a = 3 (right operand, pushed second) b = stack.pop() # b = 5 (left operand, pushed first) # Wrong: stack.append(a - b) # 3 - 5 = -2 ✗ # Correct: stack.append(b - a) # 5 - 3 = 2 ✓
Python's // floors toward negative infinity. -7 // 2 = -4. The problem wants truncation toward zero: -7 / 2 = -3. Use int(b / a) or int(float(b) / a) in Python.
# Wrong — floors toward -inf: stack.append(b // a) # -7 // 2 = -4 ✗ # Correct — truncates toward zero: stack.append(int(b / a)) # int(-7 / 2) = int(-3.5) = -3 ✓
Don't check token[0] == '-' to detect operators — that misclassifies negative numbers like "-3". Check exact equality: token in "+-*/" ortoken not in "+-*/".
["2","1","+","3","*"] → 9["1","2","+","3","*","4","-"] → 5["10","6","9","3","+","-11","*","/","*","17","+","5","+"] → 22["-7","2","/"] → -3 (not -4)
Discussion
…