Aitchbar
Aitchbar

Reputation: 23

Parsing mathematical expressions in python

So I'm currently working on a python program to parse mathematical expression strings and evaluate them. I currently have the following code:

def evaluate(string):
    expr = [a for a in string if a!=" "]    
    for i,char in enumerate(expr):
        if char=="/":
            tmp = int(expr[i-1])/int(expr[i+1])
            expr[i+1] = tmp
            expr.pop(i)
            expr.pop(i-1)
        elif char=="*":
            tmp = int(expr[i-1])*int(expr[i+1])
            expr[i+1] = tmp
            expr.pop(i)
            expr.pop(i-1)
    for i,char in enumerate(expr):
        if char=="-":
            tmp = int(expr[i-1])-int(expr[i+1])
            expr[i+1] = tmp
            expr.pop(i)
            expr.pop(i-1)
        elif char=="+":
            tmp = int(expr[i-1])+int(expr[i+1])
            expr[i+1] = tmp
            expr.pop(i)
            expr.pop(i-1)
    return expr

I gave it the input 2 / 2 + 3 * 4 - 6 * 2 and it returned ["13", "-", "12"]. Some steps I took to diagnose the problem was:
1. I moved the return expression to between the two for loops. The program then returned ["1.0", "+", "12", "-", "12"], so I know that the second loop is only evaluating the +.
2. I thought it might be a problem with the - block of code, but when I changed the input to 2 / 2 + 3 * 4 + 6 * 2 it output ["13", "+", "12"]
3. I had it print out i in the second loop, and it printed out 0,1,2. So there's the problem, it is only iterating through the first 3 elements of the list.
I get the feeling the problem has to do with modifying the list in place, and that screws up enumerate somehow. But what is the issue such that the first for loop works fine and it breaks the second? Any help would be appreciated as I am very confused

Upvotes: 1

Views: 127

Answers (1)

n1tr0xs
n1tr0xs

Reputation: 407

Use this improved code:

def evaluate(string):
    expr = [a for a in string if a!=" "]
    while( ('*' in expr) or ('/' in expr) or ('+' in expr) or ('-' in expr) ):
        for i,char in enumerate(expr):
            if char=="/":
                expr[i+1] = int(expr[i-1])/int(expr[i+1])
                del expr[i]
                del expr[i-1]
            elif char=="*":
                expr[i+1] = int(expr[i-1])*int(expr[i+1])
                del expr[i]
                del expr[i-1]
        for i,char in enumerate(expr):
            if char=="-":
                expr[i+1] = int(expr[i-1])-int(expr[i+1])
                del expr[i]
                del expr[i-1]
            elif char=="+":
                expr[i+1] = int(expr[i-1])+int(expr[i+1])
                del expr[i]
                del expr[i-1]
    return expr

Upvotes: 1

Related Questions