DEV Community

Super Kai (Kazuya Ito)
Super Kai (Kazuya Ito)

Posted on

global vs nonlocal in Python (3)

Buy Me a Coffee

*Memo:

Without a global or nonlocal statement, the closest non-local variable or a global variable can be referred to in order as shown below:

<Read(Intuitive version)>:

""" It's from the viewpoint of `third()` """

num = 2 # <- ✖
def first():
    num = 3 # <- ✖
    def second():
        num = 4 # <- 〇
        def third():
            print(num) # 4
        third()
    second()
first()
Enter fullscreen mode Exit fullscreen mode
""" It's from the viewpoint of `third()` """

num = 2 # <- ✖
def first():
    num = 3 # <- 〇
    def second():
        # num = 4 # <- Commented
        def third():
            print(num) # 3
        third()
    second()
first()
Enter fullscreen mode Exit fullscreen mode
""" It's from the viewpoint of `third()` """

num = 2 # <- 〇
def first():
    # num = 3 # <- Commented
    def second():
        # num = 4 # <- Commented
        def third():
            print(num) # 2
        third()
    second()
first()
Enter fullscreen mode Exit fullscreen mode
""" It's from the viewpoint of `third()` """

# num = 2 # <- Commented
def first():
    # num = 3 # <- Commented
    def second():
        # num = 4 # <- Commented
        def third():
            print(num) # NameError: name 'num' is not defined.
        third()        # Did you mean: 'sum'?
    second()
first()
Enter fullscreen mode Exit fullscreen mode

<Read(Unintuitive version)>:

""" It's from the viewpoint of `third()` """

def first():
    def second():
        def third():
            print(num) # 4
        num = 4 # <- 〇
        third()
    num = 3 # <- ✖
    second()
num = 2 # <- ✖
first()
Enter fullscreen mode Exit fullscreen mode
""" It's from the viewpoint of `third()` """

def first():
    def second():
        def third():
            print(num) # 3
        # num = 4 # <- Commented
        third()
    num = 3 # <- 〇
    second()
num = 2 # <- ✖
first()
Enter fullscreen mode Exit fullscreen mode
""" It's from the viewpoint of `third()` """

def first():
    def second():
        def third():
            print(num) # 2
        # num = 4 # <- Commented
        third()
    # num = 3 # <- Commented
    second()
num = 2 # <- 〇
first()
Enter fullscreen mode Exit fullscreen mode
""" It's from the viewpoint of `third()` """

def first():
    def second():
        def third():
            print(num) # NameError: name 'num' is not defined.
                       # Did you mean: 'sum'?
        # num = 4 # <- Commented
        third()        
    # num = 3 # <- Commented
    second()
# num = 2 # <- Commented
first()
Enter fullscreen mode Exit fullscreen mode

<Change(Intuitive version)>:

""" It's from the viewpoint of `third()` """

num = 2 # <- ✖
def first():
    num = 3 # <- ✖
    def second():
        num = 4 # <- ✖
        def third():
            num += 10  # UnboundLocalError: cannot access local variable
            print(num) # 'num' where it is not associated with a value
        third()
    second()
first()
Enter fullscreen mode Exit fullscreen mode

<Change(Unintuitive version)>:

""" It's from the viewpoint of `third()` """

def first():
    def second():
        def third():
            num += 10  # UnboundLocalError: cannot access local variable
            print(num) # 'num' where it is not associated with a value
        num = 4 # <- ✖
        third()
    num = 3 # <- ✖
    second()
num = 2 # <- ✖
first()
Enter fullscreen mode Exit fullscreen mode

Using both a global and nonlocal statement in the same function gets error as shown below:

<Intuitive version>:

""" It's from the viewpoint of `third()` """

num = 2 # <- ✖
def first():
    num = 3 # <- ✖
    def second():
        num = 4 # <- ✖
        def third():
            global num # SyntaxError: name 'num' is nonlocal and global
            nonlocal num
            print(num)
        third()
    second()
first()
Enter fullscreen mode Exit fullscreen mode
""" It's from the viewpoint of `third()` """

num = 2 # <- ✖
def first():
    num = 3 # <- ✖
    def second():
        num = 4 # <- ✖
        def third():
            nonlocal num # SyntaxError: name 'num' is nonlocal and global
            global num
            print(num)
        third()
    second()
first()
Enter fullscreen mode Exit fullscreen mode

<Unintuitive version>:

""" It's from the viewpoint of `third()` """

def first():
    def second():
        def third():
            global num # SyntaxError: name 'num' is nonlocal and global
            nonlocal num
            print(num)
        num = 4 # <- ✖
        third()
    num = 3 # <- ✖
    second()
num = 2 # <- ✖
first()
Enter fullscreen mode Exit fullscreen mode
""" It's from the viewpoint of `third()` """

def first():
    def second():
        def third():
            nonlocal num # SyntaxError: name 'num' is nonlocal and global
            global num
            print(num)
        num = 4 # <- ✖
        third()
    num = 3 # <- ✖
    second()
num = 2 # <- ✖
first()
Enter fullscreen mode Exit fullscreen mode

Top comments (0)