Use a list as stack/queue in Python

Python does not have native structures for stack or queue, which could otherwise be manually implemented if needed. However, list in Python is an easy alternative as stack or queue. Stack and queue share the same method append(), while stack uses pop() and queue applies pop(0) distinctively.

1. Valid Parentheses

Given a string containing just the characters ‘(‘, ‘)’, ‘{‘, ‘}’, ‘[‘ and ‘]’, determine if the input string is valid.
The brackets must close in the correct order, “()” and “()[]{}” are all valid but “(]” and “([)]” are not.
This question executes the principle of try-match-else-insert. Since the question only needs to return True/False, the logic is pretty straightforward.
# -*- coding: utf-8 -*-
def isValid(s):
a = []
for x in s:
if len(a) == 0:
a.append(x)
# Locate the three corret cases
elif ( x == ']' and a[-1] == '[' ) or ( x == '}' and a[-1] == '{' ) or ( x == ')' and a[-1] == '(' ):
a.pop()
else:
a.append(x)
if len(a) != 0:
return False
return True

if __name__ == "__main__":
testcase1 = '['
testcase2 = '(('
testcase3 = '([)]'
testcase4 = '()[]{}'
testcase5 = '([])'
for i in range(1, 6):
print isValid(eval('testcase' + str(i)))

2. Longest Valid Parentheses

Given a string containing just the characters ‘(‘ and ‘)’, find the length of the longest valid (well-formed) parentheses substring.
For “(()”, the longest valid parentheses substring is “()”, which has length = 2.
Another example is “)()())”, where the longest valid parentheses substring is “()()”, which has length = 4.
This question is the difficult version of the question above, since it asks the maximum length of valid parentheses. This time the objected to be inserted is the index of the character instead of the character itself.
# -*- coding: utf-8 -*-
def LVP2(a):
if len(a) == 0 or a == None:
return 0
last = -1
maxLen = 0
b = [] # use a buffer list as stack
for i in xrange(len(a)):
if a[i] == '(':
b.append(i)
else:
# If buffer is empty
if not b:
# Record the position before first left parenthesis
last = i
else:
b.pop()
# If buffer is empty again
if not b:
maxLen = max(i-last, maxLen)
else:
# Select the top element from the buffer
maxLen = max(i-b[-1], maxLen)
return maxLen

if __name__ == "__main__":
testcase1 = ")()())"
testcase2 = '()()()()()))))))(((((('
testcase3 = "()(()))"
testcase4 = "()(()"
testcase5 = "))))((()(("
for i in range(1, 6):
print LVP2(eval("testcase" + str(i)))

3. Evaluate Reverse Polish Notation

Evaluate the value of an arithmetic expression in Reverse Polish Notation.
Valid operators are +, -, *, /. Each operand may be an integer or another expression.
Some examples:
[“2”, “1”, “+”, “3”, ““] -> ((2 + 1) 3) -> 9
[“4”, “13”, “5”, “/“, “+”] -> (4 + (13 / 5)) -> 6
This question implements the principle of try-number-else-calcultate. The tricky part is that the stack will have to pop the elements twice.
# -*- coding: utf-8 -*-
def polish(s):
stack = []
for x in s:
# Use the int() function to make decision instead of isdigit()
try:
stack.append(int(x))
except:
# Still want to floating operation
e2 = float(stack.pop()) # the first pop-out is the second number
e1 = float(stack.pop())
if x == '+':
result = e1 + e2
elif x == '-':
result = e1 - e2
elif x == '*':
result = e1 * e2
elif x == '/':
if e2 == 0:
raise ValueError("No zero for denominator")
result = e1 / e2
else:
raise ValueError("Incorrect operator")
stack.append(int(result))
return stack[0] # transform single element list to number

if __name__ == "__main__":
testcase1 = ["2", "1", "+", "3", "*"]
testcase2 = ["4", "13", "5", "/", "+"]
testcase3 = ["3", "-4", "+"]
testcase4 = ["18"]
testcase5 = ["10","6","9","3","+","-11","*","/","*","17","+","5","+"]
for i in range(1, 6):
print polish(eval('testcase' + str(i)))

The Hardware and Software 2013 I’m Most Thankful For

It’s time of year to give thanks. As a programmer, e-book reader, blog writer and web surfer, I should express my sincere appreciation to such hardware and software (I use majority of them at daily basis and most of them are free): 0. Hardware Lenovo Thinkpad W520 (This is not free): my workhorse machine, now replaced […]

More on Technical Debt #2/2

Last week I offered some techniques for management of technical debt. In this post I offer some more.Technical debt is a debt that you incur every time you avoid doing the right thing (like refactoring, removing duplication/redundancy), thereby letting…

Kernel selection in PROC SVM

The support vector machine (SVM) is a flexible classification or regression method by using its many kernels. To apply a SVM, we possibly need to specify a kernel, a regularization parameter c and some kernel parameters like gamma. Besides the selectio…

Convert CHAR to NUM in PROC SQL

Use TO_NUMBER function in PROC SQL. proc sql;   connect to oracle (user=xxx orapw=yyy path=”@zzz”);     create table temp as       select * from connection to oracle    &nb…