The world’s leading publication for data science, AI, and ML professionals.

Global, Local and Nonlocal variables in Python

In this tutorial, let us learn the usage of Global, Local and Nonlocal variables in Python

Photo by Max Duzij on Unsplash
Photo by Max Duzij on Unsplash

First of all, I’m not the one on that image above. I’m just a benevolent writer who is here to talk about one of the most confusing concepts in Python Programming "Global, Local and Nonlocal variables". I know after reading the title you will be like "Why should I even worry about this". Well, the answer is sometimes not knowing these teeny tiny itsy bitsy would cost you a lot. So without further ado, let’s get started.

In programming languages like C/C++, every time a variable is declared simultaneously a memory would be allocated this would allocation would completely depend on the variable type. Therefore, the programmers must specify the variable type while creating a variable. But luckily in Python, you don’t have to do that. Python doesn’t have a variable type declaration. Like pointers in C, variables in Python don’t store values legitimately; they work with references highlighting objects in memory.


Topics

The list of topics that would be covered in this article is given below:

  • Variables – A quick introduction
  • Global Variables – How to get rid of UnboundLocalError
  • Local Variables – How to get rid of NameError
  • Nonlocal Variables – When and how to use them

Also, before getting started I have to tell you one thing. The whole code of this article can be found in my _GitHub Repository_ given below:

Tanu-N-Prabhu/Python


Variables

A variable is more likely a container to store the values. Now the values to be stored depends on the programmer whether to use integer, float, string or etc.

A Variable is like a box in the computer’s memory where you can store a single value. – Al Sweigart

Unlike in other programming languages, in Python, you need not declare any variables or initialize them. Please read this.

Syntax

The general syntax to create a variable in Python is as shown below:

variable_name = value

The variable_name in Python can be short as sweet as a, b, x, y, ... or can be very informative such as age, height, name, student_name, covid, ...

Although it is recommended keeping a very descriptive variable name to improve the readability.

Rules

All set and done, there are some rules that you need to follow while naming a variable:

  • A variable name must start with a letter or the underscore character
  • A variable name cannot start with a number
  • A variable name can only contain alpha-numeric characters and underscores. For example, anything like this is valid: **A-z, 0–9, and **_
  • Variable names are case-sensitive (height, Height, and HEIGHT are three different Variables names)

Example

Below given is an example to properly initialize a value to a variable:

# This is a valid and good way to assign a value to a variable
# Let's assign values to variables to calculate the area of a circle
pi = 3.142            # I could have also used "math" library 
radius = 5            # Interger value for radius
area_of_circle = 0    # Used to store the value of area of circle
area_of_circle = pi * (radius) ** 2        # Area = (PI * R^2)
print("The area of the circle is: ", area_of_circle)

The output of the above code is given below:

The area of the circle is:  78.55

Pictorial Example (Skim it quickly)

I believe just by seeing a picture or an image, the concepts can be understood more quickly. Below is the pictorial representation of a variable and it being stored in the memory.

Photo by Author - Tanu Nanda Prabhu
Photo by Author – Tanu Nanda Prabhu
Photo by Author - Tanu Nanda Prabhu
Photo by Author – Tanu Nanda Prabhu

Global Variables

Same old definition

In Python or any other programming languages, the definition of global variables remains the same, which is "A variable declared outside the function is called global function". We can access a global variable inside or outside the function.

Creating a global variable and accessing it

Let’s use the same example from above to understand the concept of accessing the variable inside and outside the function.

pi = 3.142       # I could have also used "math" library (math.pi)
radius = 5       # Interger value for radius
def circle():
    area_of_circle = pi * (radius) ** 2
    print("The area of the circle is: ",   area_of_circle)
    circumference_of_circle = 2 * pi * radius
# Accessing the global variables outside the function
print("The circumference of the circle: ", circumference_of_circle)
# Accessing the global variables inside the function
circle()     

The output for the above code is given below:

The circumference of the circle:  31.419999999999998 
The area of the circle is:  78.55

There you go this is the specialty of global variables. As seen in the above example I have used two common variables pi and radius to calculate the area of the circle which is declared inside a function and area of the circumference which is calculated outside the function. For both these calculations, we are using the same common variables.

Understanding "UnboundLocalError" in detail

Now let’s take the same old example and try to update the radius by 2 (multiply by 2)

pi = 3.142       # I could have also used "math" library (math.pi)
radius = 5       # Interger value for radius
def circle():
    radius = radius * 2         # Update the radius by (x 2)
    area_of_circle = pi * (radius) ** 2
    print("The area of the circle is: ", area_of_circle)
circle()     # Accessing the global variables inside the function

Now I know you might be like "there is no necessity" of this extra step *`radius = radius 2** we can directly do this in the initial step by assigning the value to the radius as 10 i.e. **radius = 10`**. I know but I am trying to introduce a concept here. Please bear with me.

As seen in the above code, if you try to update the radius and then execute this piece of code you will be surprised. Don’t be excited and say "I did it" because you didn’t, rather you will be prompted by an error called UnboundLocalError. More likely the error looks like this.

UnboundLocalError: local variable 'radius' referenced before assignment

The reason for this error is that the variable radius is local and it cannot be updated as above. Here, you can make it a global variable. Now how to do it. Please see the below code snippet.

pi = 3.142       # I could have also used "math" library (math.pi)
radius = 5       # Interger value for radius
def circle():
    global radius               # Making raduis a global variable
    radius = radius * 2         # Update the radius by (x 2)
    area_of_circle = pi * (radius) ** 2
    print("The area of the circle is: ", area_of_circle)
circle()     

Now when you execute the code, it executes with no problem. Because now it explicitly declared as a global variable. The output of the above code is given below:

The area of the circle is:  314.2

Time to test your knowledge in the long run. Two years back there was this one question asked in Stack Overflow about UnboundLocalError. The form is now closed for answers because there are already tons of answers present. You can hop in there and try to answer it and understand it more clearly.


Local Variables

Same old definition

In Python or any other programming languages, the definition of local variables remains the same, which is "A variable declared inside the function is called local function". We can access a local variable inside but not outside the function.

Creating a local variable and accessing it

We use the local variables inside a function and not try to access them outside those functions. Hence the name local. But the good part is we can access those variables within the functions itself.

def circle():
    pi = 3.142    # I could have also used "math" library (math.pi)
    radius = 5    # Interger value for radius
    area_of_circle = pi * (radius) ** 2
    print("The area of the circle is: ",   area_of_circle)
    circumference_of_circle = 2 * pi * radius
# Accessing the global variables inside the function
circle()

The output of the above code is:

The area of the circle is:  78.55

There you go this is the specialty of local variables. As seen in the above example I have used two common variables pi and radius to calculate the area of the circle which is declared inside a function. So accessing these variables will not create any problem. But what happens if we try to access them outside the function. See the next section below.

Understanding "NameError" in detail

Let’s use the same example from above and access the variables declared inside the function:

def circle():
    pi = 3.142    # I could have also used "math" library (math.pi)
    radius = 5    # Interger value for radius    
    area_of_circle = pi * (radius) ** 2
    print("The area of the circle is: ",   area_of_circle)
    circumference_of_circle = 2 * pi * radius
# Accessing the global variables outside the function
print("The circumference of the circle: ", circumference_of_circle)
# Accessing the global variables inside the function
circle()

When you execute the above code, you will be prompted by a NameError. More likely the error looks like this

NameError: name 'pi' is not defined

The reason for this error is as we are trying to access a local variable pi and radius in a global scope whereas the local variable only works inside `circle()or local scope. There is a way to solve it by declaring **pi** and **radius`** as global or declaring them outside the function. Where any function can access them.


Nonlocal Variables

Same old definition

In Python or any other programming languages, we often use the nonlocal variable inside nested functions. Now, what do I mean by nested functions?

Nested Functions

In general, a nested function is a set of functions declared inside another function. Given below is an example of a nested function.

def circle():
    pi = 3.142   # I could have also used "math" library (math.pi)
    radius = 5   # Interger value for radius
    area_of_circle = pi * (radius) ** 2
    def circumference():
        # Formula for circumference
        circumference_of_circle = 2 * pi * radius    
        return circumference_of_circle
    print(circumference())    # Calling the circumference function
    return area_of_circle
print(circle())     # Calling the circle function

On executing this piece of code you will get the following as the output

31.419999999999998 
78.55 

Creating a nonlocal variable and accessing it

Let us now try to update the radius by 2 (multiply by 2) inside the `circumference(). The reason that I'm specifically insisting to do this because as soon as you write **radius = radius * 2** and run the code you will be prompted by **UnboundLocalError** seeing this you will change it to a global variable by saying **global radius** but this time you will get a new error as **NameError**. And now you will be baffled, don't know what to do. There is a simple way to solve this "_**Go read the definition of a nonlocal variable**_". Whenever there is a nested function you need to use a **nonlocal`** variable. That’s it problem solved. Below is the way to create a nonlocal variable and access it.

def circle():
    pi = 3.142   # I could have also used "math" library (math.pi)
    radius = 5   # Interger value for radius
    area_of_circle = pi * (radius) ** 2
    def circumference():
        nonlocal radius         # Nonlocal variable
        radius = radius * 2
        # Formula for circumference
        circumference_of_circle = 2 * pi * radius    
        return circumference_of_circle
    print(circumference())    # Calling the circumference function
    return area_of_circle
print(circle())     # Calling the circle function

On executing this code you will get the output as

62.839999999999996 
78.55 

Conclusion

This is the end of the article titled "Global, Local and Nonlocal variables in Python". I hope you guys learned a thing or two by reading this article. Through this article, you learned how to get rid of two important Python errors such as NameError and UnboundLocalError which were troubling you all these days or years or whatever. Now you can easily debug these two errors with a smile on your face without losing a sweat. If you have any comments or suggestions about this article, then the comment section is all yours. Stay tuned for more updates, until then goodbye. Stay safe and happy coding and see you next time.


Related Articles