How To Resolve UnboundLocalError On Local Variable When Reassigned After The First Use?

Summary: To resolve an UnboundLocalError when the local variable is reassigned after the first use, you can either use the global keyword or the nonlocal keyword. The global keyword allows you to modify the values of a global variable from within a function’s local scope while the nonlocal keyword provides similar functionality in case of nested functions.

Problem: Given a local variable. How to resolve an UnboundLocalError when the local variable is reassigned after the first use?

Example:

val = 100


def func():
    val = val + 100
    print(val)


func()

Output:

Traceback (most recent call last):
  File "C:/Users/Shubham-PC/PycharmProjects/pythonProject1/main.py", line 9, in <module>
    func()
  File "C:/Users/Shubham-PC/PycharmProjects/pythonProject1/main.py", line 5, in func
    val = val + 100
UnboundLocalError: local variable 'val' referenced before assignment

Try It Yourself:

Before we deal with the solutions to our problem, we must understand the the root cause behind UnboundLocalError.

Root Cause Of UnboundLocalErrors:

When a variable is assigned within a function, it is treated as a local variable by default in Python. If a local variable is referenced before a value has been assigned/bound to it, an UnboundLocalError is raised. In the above example when the variable 'val' is read by the Python interpreter inside the func() function, it assumes that 'val' is a local variable. However, it soon realizes that the local variable has been referenced before any value assigned to it within the function. Thus it throws an UnboundLocalError.

In other words, we can only access a global variable inside a function but cannot modify it from within the function (unless you force a global or nonlocal assignment using the global or nonlocal keywords).

Note: The parent class of all Python exceptions is BaseException. The following diagram represents the exception hierarchy of the UnboundLocalError.

UnboundLocalError Exception Hierarchy

Now that we know why and when an UnboundLocalError is raised, let us have a look at the probable solutions to overcome this error.

Method 1: Using The global Keyword

We can use the global keyword to access and modify a global variable from a local scope or a function. Any variable created outside a function is global by default while any variable created within the function is local by default. Thus, to modify a global variable from within the function and avoid an UnboundLocalError we can use the global keyword.

Let us have a look at the following code which simplifies the above concept:

val = 100
print("Value at First Usage: ", val)


def func():
    global val
    val = val + 100
    print("Output after Modification within func(): ", val)


func()

Output:

Value at First Usage:  100
Output after Modification within func():  200

Method 2: Using nonlocal Keyword

The nonlocal keyword is used when we have a nested function. In such a situation local scope of a variable might not be defined, that is, the scope of a variable is neither local nor global.

Let us have a look at the following example to understand the usage of the nonlocal keyword to deal with our problem.

def func():
    val = 50
    print("Output of func:", val)

    def foo():
        nonlocal val
        val = val + 100
        print("Output of foo:", val)

    foo()
    print("Output of func() after changes made to foo():", val)


func()

Output

Output of func: 50
Output of foo: 150
Output of func() after changes made to foo(): 150

In the above program, the nonlocal keyword is used with the variable val inside the nested function foo() to create a nonlocal variable. If the value of the nonlocal variable changes, the changes are reflected in the local variable as well.

Disclaimer: the nonlocal keyword works only in Python 3 and above.

Method 3: Using A Mutable Object

Since nonlocal does not work in versions of Python before Python 3, you can use a mutable object like a python dictionary, to store the values if you do not want to create a global variable.

Let us have a look at the following program to understand the usage of a mutable object in order to overcome the UnboundLocalError.

variables = {  # creating a mutable object/dictionary
    'val': 100
}
print('Output before Modification of val: ', variables['val'])


def func():
    variables['val'] += 50
    print('Output after Modification of val: ', variables['val'])


func()
Output before Modification of val:  100
Output after Modification of val:  150

Method 4: Passing Parameters To The Function

A quick fix to our problem is fairly simple. Instead of using a global variable, we can pass parameters to the defined function to avoid an UnboundLocalError. Let us have a look at the following code to see how this can be done:

val = 100
print("Value of val at first use: ", val)


def func(v):
    v = v + 100
    print("Output of val after modification:", v)


func(val)

Output:

Value of val at first use:  100
Output of val after modification: 200

Global Keyword vs Nonlocal Keyword

Before concluding this article, let us have a look at the key differences between a global and nonlocal variable/keywords.

  1. Unlike the global keyword, the nonlocal keyword works only in Python 3 and above.
  2. The global keyword can be used with pre-existing global variables or new variables whereas the nonlocal keyword must be defined with a pre-existing variable.

Here’s a brainstorming exercise for you:

Exercise: Can you guess the output of this code?

Conclusion

From the above discussion we learned that to deal with UnboundLocalError in our code we can use one of the following methods:

  1. Use the global keyword.
  2. Use the nonlocal keyword in case of nested functions.
  3. Use a mutable object.
  4. Pass parameters to a function.

I hope that you found this article helpful and after reading it you can deal with UnboundLocalError with ease. Please stay tuned for more interesting articles.

Where to Go From Here?

Enough theory, let’s get some practice!

To become successful in coding, you need to get out there and solve real problems for real people. That’s how you can become a six-figure earner easily. And that’s how you polish the skills you really need in practice. After all, what’s the use of learning theory that nobody ever needs?

Practice projects is how you sharpen your saw in coding!

Do you want to become a code master by focusing on practical code projects that actually earn you money and solve problems for people?

Then become a Python freelance developer! It’s the best way of approaching the task of improving your Python skills—even if you are a complete beginner.

Join my free webinar “How to Build Your High-Income Skill Python” and watch how I grew my coding business online and how you can, too—from the comfort of your own home.

Join the free webinar now!