Johnny Metz
Johnny Metz

Reputation: 5965

Determine even/odd iteration in Python recursive function

Let's say I have the following Python dictionary:

d = {1: {2: {3: {}}, 4: {5: {}}, 6: {}}, 7: {8: {}}}

I can recursively walk through the dictionary using the following function:

def recurse(d):
    for k, v in d.items():
        print(f"key: {k}")
        if v:
            recurse(v, level + 1)

I only want to print the key if we're on an EVEN iteration. Looks like I can do this using a global count variable:

count = 0

def recurse_toggle(d):
    global count
    for k, v in d.items():
        if count % 2 == 0:
            print(f"key: {k} (count={count})")
        count += 1
        if v:
            recurse_toggle(v)
# key: 1 (count=0)
# key: 3 (count=2)
# key: 5 (count=4)
# key: 7 (count=6)

However, I don't want to use a global variable because it's bad practice. How can I refactor this function to do this WITHOUT using a global variable? Note I don't necessary need the count parameter (maybe passing in an is_even parameter works better?).

Upvotes: 0

Views: 146

Answers (2)

Hymns For Disco
Hymns For Disco

Reputation: 8395

If you don't want count to be global, simply move everything down into a local scope

def recurse(d):
    count = 0

    def _recurse(d):
        nonlocal count
        for k, v in d.items():
            if count % 2 == 0:
                print(f"key: {k} (count={count})")
            count += 1
            if v:
                _recurse(v)
    _recurse(d)

Also keep in mind that the order of dict items should not be relied on, as this order is not guaranteed

Upvotes: 0

abc
abc

Reputation: 11929

You can just keep track of the level and increment it at each recursive call. It is initialized at 0.

>>> def recurse_toggle(d, level=0):
...     for k, v in d.items():
...         if level % 2 == 0:
...             print(f"key: {k}")
...         recurse_toggle(v, level+1)
... 
>>> recurse_toggle(d)
key: 1
key: 3
key: 5
key: 7

Upvotes: 1

Related Questions