But this answer suggests that the problem is with the purpose of x. If this is the case, printing should work fine, right?
You must understand the order in which everything happens. Before your python code is even compiled and executed, something called a parser reads the python code and checks the syntax. Another thing the parser does is variable labels as local ones. When the analyzer sees the assignment in the code in the local area, the variable on the left side of the assignment is marked as local. At this point, nothing was compiled yet - not to mention execution, and therefore the appointment does not occur; the variable is simply marked as a local variable.
Upon completion of the analyzer, the code is compiled and executed. When execution reaches the print statement:
def main(): x = 10
the print statement looks as if it should go ahead and print x in the scope (βEβ in the LEGB search process). However, since the parser previously marked as a local variable inside f (), python does not go past the local area (βLβ in the LEGB search process) to search for x. Since x was not assigned in the local area at the time "print x" was executed, python spits out an error.
Note that even if the code in which the assignment occurs is NEVER executed, the parser still marks the variable to the left of the destination as a local variable. The parser has no idea how everything will be executed, so it blindly searches for syntax errors and local variables in your file - even in code that can never be executed. Here are some examples of this:
def dostuff (): x = 10 def f(): print x if False:
The parser does the same when marking local variables:
def dostuff (): x = 10 def f(): print x if False:
Now let's see what happens when you run this last program:
Traceback (most recent call last): File "1.py", line 11, in <module> f() File "1.py", line 4, in f print x UnboundLocalError: local variable 'x' referenced before assignment
When the expression "print x" is executed, since the parser marked as a local variable searches for x in the local scope.
This function is not unique to python - it happens in other languages.
As for the array example, when you write:
x[0] = x[0] + 1
which tells python to go to an array named x and assign it to the first element. Since no x name is assigned in the local scope, the analyzer does not mark x as a local variable.