Python: Return possibly not returning value

2020-05-08 23:57发布

Hello Stack Overflow Community,

I am trying to write a program that checks Fermat's Last Theorem. The issue I am running into is that an error appears saying "NameError: name 'a' is not defined. However, I define 'a' in my first function and return its value at the end of the function.

I am trying to use the inputed values from the first function in the second function so the user can define the parameters.

Am I misunderstanding how to leverage "Return"? All help is greatly appreciate and will keep me sane.

def input_fermat():
    a=input('Enter the first variable \'a\': \n')
    b=input('Enter the second variable \'b\': \n')
    c=input('Enter the third variable \'c\': \n')
    n=input('Enter the exponential variable \'n\': \n')

    return a, b, c, n

def check_fermat(a,b,c,n):

    calc_1=a**n
    calc_2=b**n
    calc_3=c**n

    if n>2 and int(calc_1) + int(calc_2) == calc_3:
        print('Holy smokes, Fermat was wrong!')
    else:
        print('No that doesn\'t work.')

input_fermat()
check_fermat(a,b,c,n)

5条回答
ら.Afraid
2楼-- · 2020-05-09 00:34

You are not storing the values that the function input_fermat returns. Try:

a, b, c, n = input_fermat()

check_fermat(a,b,c,n)
查看更多
▲ chillily
3楼-- · 2020-05-09 00:39

Returned values don't just automatically show up in your namespace, you have to assign them to something.

a, b, c, n = input_fermat()
查看更多
在下西门庆
4楼-- · 2020-05-09 00:48

The variables a, b, c, n defined in input_fermat only exists within the function, that's why you return them, but when you call the function you aren't saving them anywhere. You should replace:

input_fermat()

By:

a, b, c, n = input_fermat()

Or you can directly pass the return value of input_fermat to check_fermat like this:

check_fermat(*input_fermat())
查看更多
冷血范
5楼-- · 2020-05-09 00:57

This is happening because those variables are defined locally and are not available in check_fermat's namespace.

Refer to the LEGB-rule.

What you can do is define all of those variables using the global keyword in the function definition, although this isn't usually the best approach. You'll also want to cast all of your inputs to ints since input() will return a string.

查看更多
疯言疯语
6楼-- · 2020-05-09 00:59

Variables a,b,c and n, which you receive as input in input_fermat(), are only available within the body of that function; once you return, you're out of input_fermat()'s scope and the values in a,b,c and n are handed off to whatever variables you called input_fermat() to assign .

A function's scope means the only variables available in any given function are

  • those that are declared in the body of the function
  • those passed to the function as arguments in parentheses.
  • variables declared globally

In check_fermat(),this means you could re-use variables a,b,c and for something other than the input, if you wanted (because a new function means a new scope).

But, in the code shown below, we decide that a,b,c and n in check_fermat() are going to be the same thing as a,b,c and d in input_fermat() with the declaration a,b,c,n = input_fermat(). This is a decision we chose to make; it's arbitrary.

Here's an edited version of your function that accomplishes what I think you were going for:

#Global variables would be declared up here, before all other function declarations.
#Global variables would be available to all the functions that follow.

def input_fermat(): #if there were arguments in these parentheses they'd be included in input_fermat scope
    # input_fermat() scope begins
    a=int(input('Enter the first variable \'a\': \n'))
    b=int(input('Enter the second variable \'b\': \n'))
    c=int(input('Enter the third variable \'c\': \n'))
    n=int(input('Enter the exponential variable \'n\': \n'))

    return a, b, c, n
    #input_fermat() scope ends

def check_fermat(): #if there were arguments in these parentheses they'd be included in check_fermat scope
    #check_fermat() scope begins

    #just as you returned 4 variables at once in input_fermat(), 4 variables can be assigned at once here
    a,b,c,n = input_fermat() #need to assign because a, b, c, n from input_fermat() no longer in scope
    calc_1=a**n
    calc_2=b**n
    calc_3=c**n

    if n>2 and int(calc_1) + int(calc_2) == calc_3:
        print('Holy smokes, Fermat was wrong!')
    else:
        print('No that doesn\'t')

    #python implicitly does a `return None` here
    #check_fermat() scope ends

check_fermat()

Note that because of the scopes of these functions, I could have declared the variables in check_fermat() as follows and it would all still work (try running this code for yourself to see)

def input_fermat(): 
    a=int(input('Enter the first variable \'a\': \n'))
    b=int(input('Enter the second variable \'b\': \n'))
    c=int(input('Enter the third variable \'c\': \n'))
    n=int(input('Enter the exponential variable \'n\': \n'))

    return a, b, c, n

def check_fermat():
    any,variable,names,go = input_fermat()
    calc_1=any**go
    calc_2=variable**go
    calc_3=name**go

    if n>2 and int(calc_1) + int(calc_2) == calc_3:
        print('Holy smokes, Fermat was wrong!')
    else:
        print('No that doesn\'t')

check_fermat()

The Process of execution (for both code snippets) goes like this:

  1. check_fermat() on the last line is executed because it's the only function called (not just defined) in our .py file.
  2. Python looks for the definition of check_fermat() to execute it 3.Python finds input_fermat() is called inside check_fermat and goes looking for input_fermat()s definition.
  3. Python finds the definition, executes the function and asks for input.
  4. Input is returned back to check_fermat() and is used to compute Fermat's Last Theorem.
  5. The rest of check_fermat() is carried out (output is printed to terminal). Then, check_fermat() returns None, ending the function call with no variables to return.
查看更多
登录 后发表回答