0

In this program I have the user enter an equation and display it back to them.

The problem I'm having is that when I call the function that asks for the equation again I get a TypeError. I have know why I keep getting this error and have tried multiple ways to try and fix it. help?

import parser
def eq():   
    global eq
    global eq_parsed
    while True:
        eq = input('f(x) = ')
        try:
            eq_parsed = parser.expr(eq).compile()
            x=0
            eval(eq_parsed)
            break
        except:
            print("invalid equation")
    print ("Your equation: f(x)=", eq)
    mark=True
    return (mark)
T=True
mark=False
while T==True:
    if mark==False:
        n=input("\nStart? (y/n): ")
    elif mark==True:
        n=input("\nStart Again? (y/n): ")
#----------------------------------------
    if n=='y':
        mark = eq()
    elif n=='n':
        break
    else:
        print("Invalid Input*")
1
  • 1
    I would strongly suggest against the use of global variables. If a function needs to use them you should be passing them in as parameters. Commented Jul 28, 2014 at 20:23

3 Answers 3

4

Your problem is that you use eq to be both the function name and a global variable. So when you write eq(), the name eq refers to the global variable.

def eq(): # eq refers to this function
    global eq 
    ....
    eq = input('f(x) = ') # now eq refers to the string object return by input
....
mark = eq() # and a string object is not callable

You'll make your life a lot easier if you use a different name for the function and the global string variable. And the other way to make things a lot cleaner is to stop using global, and return anything that the caller needs in the return statement of the function.

def eq():   
    while True:
        eq_input = input('f(x) = ')
        try:
            eq_parsed = parser.expr(eq).compile()
            x=0
            eval(eq_parsed)
            break
        except:
            print("invalid equation")
    print ("Your equation: f(x)=", eq_input)
    return True, eq_input, eq_parsed

And then call it like this:

mark, eq_input, eq_parsed = eq()

Not that you currently appear to use the values assigned to eq_input and eq_parsed outside the function. In which case, you don't need to return them at all and they can remain local to the function.

It is idiomatic to write

if val:

rather than

if val == True:

And similarly

if not val:

is preferred over

if val == False:
Sign up to request clarification or add additional context in comments.

Comments

2

You have named your function eq(), and you also have a global variable named eq. You can't have both. Since Python (generally) evaluates from the top down, first the function's name is assigned to the identifier eq, then later on the results of the input() call are. When you try to call eq() down at the bottom, you get the error, as Python thinks you're trying to call a string.

Perhaps name the variable equation, to avoid confusion.

Comments

1
def eq():   
     global eq
     # ...
     eq = input('f(x) = ')

globally redefines eq to the content of input when eq is called, which is a string. use different names for your functions and variables.

Therefore, you can call eq exactly once, and then it refers to a string and no longer to a function.

Comments

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.