0

I wonder how integer variable changes its value in recursion calls. I have a recursion function finding the max of an array as the following in python3

def recurse(arr,maxnum,size):
    #base case: when it reaches the end of an array
    if size== len(arr):
        return 

    maxnum= max(maxnum,arr[size])
    print('current max in recursion',maxnum)
    recurse(arr,maxnum,size+1)

arr = [5, 1, 6, 0, 3, 7, 4, 2]
maxnum = -99999
recurse(arr,maxnum,0)
print('max result',maxnum)

after run the code, the maxnum was still -99999 without any changes, but I got the following print result

current max in recursion 5
current max in recursion 5
current max in recursion 6
current max in recursion 6
current max in recursion 6
current max in recursion 7
current max in recursion 7
current max in recursion 7
max result -99999

why is it that maxnum gets back to its original variable after recursion calls. However, if I create a array-like variable as the following, it works

def recurse(arr,maxnum,size):
    if size== len(arr):
        return 

    maxList[0] = max(maxList[0],arr[size])
    print('current max in recursion',maxList[0])
    recurse(arr,maxList[0],size+1)


root = [5, 1, 6, 0, 3, 7, 4, 2]
maxnum=-9999
maxList = [-999]
recurse(root,maxList[0],0)
print('list',maxList[0])

current max in recursion 5
current max in recursion 5
current max in recursion 6
current max in recursion 6
current max in recursion 6
current max in recursion 7
current max in recursion 7
current max in recursion 7
list 7
The-Han-Emperor
  • 337
  • 1
  • 2
  • 12
  • `maxnum` inside function is local variable - so you don't change directly values in global variable `maxnum` - at start both keep reference to the same value but when you assign new value like integer or string then it assigns to local variable reference to new value but it doesn't change global variable. But if you keep reference to list or dictionary then you change reference inside the same list/dict. Maybe run it on http://www.pythontutor.com/ to see references – furas May 17 '20 at 10:17
  • See also [Modifying function arguments](https://stackoverflow.com/questions/45111055/modifying-function-arguments). And don't take the first answer too literally, look at the other ones too. – Keldorn May 17 '20 at 10:19
  • 1
    BTW: find information about [Mutable vs Immutable Objects in Python](https://medium.com/@meghamohan/mutable-and-immutable-side-of-python-c2145cf72747) – furas May 17 '20 at 10:20
  • https://stackoverflow.com/questions/575196/why-can-a-function-modify-some-arguments-as-perceived-by-the-caller-but-not-oth/575337#575337 – Keldorn May 17 '20 at 10:33

1 Answers1

0

maxnum is a local variable in your function because you assign to it, so it is unrelated to the global maxnum. It would be clearer if you had used different variable names:

def recurse(arr,maxnum,size):
    #base case: when it reaches the end of an array
    if size== len(arr):
        return 


    maxnum= max(maxnum,arr[size])
    print('current max in recursion',maxnum)
    recurse(arr,maxnum,size+1)

arr = [5, 1, 6, 0, 3, 7, 4, 2]
max_initial_value = -99999
recurse(arr,max_initial_value ,0)

This would raise a NameError, as maxnum doesn't exist here

print('max result',maxnum)
# NameError: name 'maxnum' is not defined

and this would print the original, unmodified value:

print('max result', max_initial_value)
max result -99999

In your second example, you never assign anything to myList, so it isn't considered local by Python. You update the only, global myList.

Thierry Lathuille
  • 23,663
  • 10
  • 44
  • 50