Why does this code pull the same info inside and outside of function?

If this yields the answer inside the function yields the output below:

ip1 = “10.20.30.40”

def myFunction():

    ip1 = "192.168.100.200"
    print("This IP address is: " + ip1)
myFunction()

Output: This IP address is: 192.168.100.200

Then why does this use the number 105 when its outside of the function, as well as

answer = 105

# do not edit below this line

number = 105

def sample_function():

    number = 37
    return number

print(number)

if number == answer

print(f"Submitted answer: {answer} | Correct!")

else:

    print(f"Submitted answer: {answer} | Try again")

AND

answer = 105

# do not edit below this line

number = 105

def sample_function():

    number = 37
    return number
print(number)

sample_function()

if == answer:

print(f"Submitted answer: {answer} | Correct!")

else:

print(f"Submitted answer: {answer} | Try again")

AND

answer = 105

# do not edit below this line

number = 105

def sample_function()

    number = 37
    return number
print(number)

if number == answer:

print(f"Submitted answer: {answer} | Correct!")

else:

print(f"Submitted answer: {answer} | Try again")

sample_function()

All yield 105 as the answer, despite moving all of the items within the function? Shouldn’t the encapsulation within the function force the code to use 37 instead of the 105 which is outside of the function?

It’s kinda hard to follow the scopes of your code as you have it formatted, could you update using a single codeblock?

4 Likes

This is just how its shown on the page from the website. The first is the example they give about how that function works and it shows the items within it. The next 3 examples are all the same code, just switched up a little bit to show what I tried to get it to use the “number” within the function(37) instead of the one above it (105). I separated all 3 of them with “AND”. I wouldnt think they would all go in a single block. Im trying to figure out why it keeps using the number outside of the function if the print and if/else statements are within.

Hello, @Jayfaas, and welcome to the Python community!

Please see the following pages for useful information about this forum:

Your Python code would be much easier to read if it were formatted for proper display. The first of the two links listed above provides guidance regarding how to format Python code whenever you ask questions or help other users here. Specifically, that information is offered in the section How do I post code snippets, error messages etc?.

What @Quercus and @hwelch wrote, but also, in spite of the code being unreadable, I think …

You haven’t understood that a variable becomes local to a function if it is assigned in that function. You can change that with the global and nonlocal keywords, but you should understand first what happens by default.

1 Like

Within the official Python document 4. Execution model, the 4.2. Naming and binding section may be of help. Focus especially on 4.2.2. Resolution of names.

1 Like

is that not what the “number = 37” is doing? I thought this would have assigned it inside the function?

I agree. I think you have posted 4 blocks of code, and if you put three backticks at the beginning of each, and three backticks at the end of each, you’ll be amazed how much more readable it all gets.

Yes. It creates a new variable, locally inside sample_function, assigns 37 to it and returns that value. So the value of sample_function(), every time you call it, is 37, which never affects, or is altered by, the value of number at the global scope.

1 Like

Below is some code adapted from that in the original post, followed by output. Hopefully, this will help illuminate the relevant concepts.

Code:

answer = 105 # global variable, answer
number = 105 # global variable, number
print(f"global variable, answer, before function execution: {answer}")
print(f"global variable, number, before function execution: {number}")

def sample_function():
    # create local variable, number
    number = 37 
    print(f"global variable, answer, as visible from inside function: {answer}")
    print(f"local variable, number, during function execution: {number}")
    # return the value referred to by local variable, number, to calling statement,
    # and terminate function execution
    return number 

print("--------") # dashes before function execution

returned_value = sample_function() # calls the function and saves the returned value

print("--------") # dashes after function execution

print(f"global variable, returned_value, after function execution: {returned_value}")
print(f"global variable, answer, after function execution: {answer}")
print(f"global variable, number, after function execution: {number}") # unchanged

Output:

global variable, answer, before function execution: 105
global variable, number, before function execution: 105
--------
global variable, answer, as visible from inside function: 105
local variable, number, during function execution: 37
--------
global variable, returned_value, after function execution: 37
global variable, answer, after function execution: 105
global variable, number, after function execution: 105

Thank you for this very detailed post. I really do appreciate you trying to help, but I honestly think that some people are made for programming and some arent. Those that can decipher this are just a different type of people. Nonetheless I have to get through it, so I will keep hacking away at it.

```
answer = 105

# do not edit below this line

number = 105

def sample_function():
    number = 37
    if number == answer:
        print(f"Submitted answer: {number} | Correct!")
    else:
        print(f"Submitted answer: {number} | Try again")
    return
```

I didnt realize until reading it a little more and seeing your example that “return” here essentially ended the function, and I was putting the items outside of it I guess? Putting the print function before return made it print the number within “sample_function”, however when I added the if/else before the “return number”, I was thinking that this would cause it to use the number within the function and compare it with global variable “answer” but I was wrong on that. I am not understanding this whole inside/outside function relationship I guess. Can you not do if/else within a function by using local and global variables? Above is just one of the many different ways I tried putting it to get an understanding of what its doing.

Oddly enough I went back to my classwork and searched for the “return” function to try and get a better understanding, and i’m still like 5 chapters away. Not sure why they would put it here.

Persistence in the face of challenges is one of the attributes of a good programmer.

That may be exactly the persistence that is needed!

Please continue to ask questions when you have them.

A function definition begins with its header, and thereafter, the extent of the body of the function is specified by the indentation of the statements that follow. A return statement is not a boundary that demarcates the end of the definition of the function. Rather, a return statement is one that terminates execution of a function if and when that return statement is executed, and it returns a value that could be utilized by the statement that called the function.

That return statement, which is quoted from the sample_function you just posted, does not specify a value to be returned to the calling statement, therefore it returns the value None. As that function is written, that return is unnecessary, because execution of the function would terminate anyway when that execution reaches the function’s final line of code.

As is typical with programming languages, names, such as those of variables, have scope, which is the extent of where that name is recognized and is accessible. If a variable is initiated and therefore defined in a line a code outside the boundaries of all functions and classes in a program, it has a global scope, which means that its value could potentially be accessed throughout the program. However, if a local variable with the same name is created inside a function, the global variable with the same name is not the one that would be accessed when that name is used inside the function.

This assignment statement inside the sample_function above is what establishes number as a local variable:

    number = 37

That is because an assignment to a name within a function creates a local variable by that name, unless that name has specifically been declared as global or nonlocal within the function. Since number is a local variable within the sample_function function, any use of the name within that function refers to the local variable rather than to the global one by the same name.

1 Like

I second this. This is one of the reasons I usually skip the Python Help section :rofl:
I’m not saying we have to follow the… high standards of StackOverflow, but at least a minimum.

I spend a lot of time on the ESRI forums to help out with arcpy related questions and somehow the formatting there is even worse. I’ve seen people copy and paste the the output of `cat` with no formatting at all for 1000 line scripts.

So join me in flagging such posts as inappropriate. Asking for help but dumping an unreadable mess is not ok.

1 Like

Blade Runner forums :smiley:

So I was just unlucky – or maybe lucky. Every time I posted something on a forum, a StackSomething or an issue tracker, that was not perfect, it was closed or downvoted immediately T_T

I prefer to continue to just ignore them :slight_smile:

@Jayfaas : this is why everyone has given you such a hard time about marking up your code properly. If you don’t, the the forum software messes up the indentation (which is fine for ordinary text), and we can’t tell where the function scope ends either.

As @Quercus has explained, the indentation of a function body defines a scope, a sort of private box within which you can define and use names without accidentally altering a variable elswhere that happens to have the same name. (Most indentation does not do that, not the indentation of your if-else for example.)

You can refer to things outside the box (scope), and it means the same thing, but any name that gets assigned to inside the box, has only its local meaning, even if the computer hasn’t assigned it a value yet.

You will get used to stepping through instructions, pretending to be the computer, as a way to understand what code does. When it steps onto a return statement, the computer is catapulted out of that scope, back to where it was when it called the function. All the local variables created inside the box evaporate, except for whatever value followed the return, which becomes the return value of the function.

If the computer calls the function again, it gets a new box,where the local variables have no value yet.

2 Likes

The below code is simply a way to codify the wording from the others.

ip_addr = "192.168.1.1"

def get_ipv4(ip_addr = "172.17.211.192"):
    return ip_addr

# Will return the class B ipV4 address, the default value of the function
print(get_ipv4())
# Will return the class A private ipV4 address, One argument pass to the function
print(get_ipv4("10.0.0.1"))
# Will return the class C ipV4 address, defined outside of the function
print(get_ipv4(ip_addr))
# Will return the class C ipV4 address, defined outside of the function
print(ip_addr)