Python’s Way of Handling Function Arguments
Pass by Value or Pass by Reference
In python a function is a block of code that gets executed only when it’s called and may return some data as a result of the call. We can pass any number of arguments to a function.
In most programming languages arguments are are passed either by value or by reference. When we pass function arguments by value, those arguments becomes independent copies of the actual parameters and any changes made to the formal parameters aren’t reflected in the actual parameters passed. In contrast, when you pass function arguments by reference, those arguments refers to the actual parameters and no copies are created i.e. any changes made in the formal parameters gets reflected in the actual parameters.
Now like most programming languages does python too support, ‘pass by value’ or ‘pass by reference’?
Fun Fact: Python has it’s own little peculiar yet somewhat unique way of handling function arguments.
Let’s understand with the help of some examples:
From this you might think that python passes arguments by value, as no change is reflected in the actual value of x , but before reaching to a conclusion have a look at the next example.
Now the above example leaves us in a dilemma, as the changes made in the list ‘l’ in the add() function are visible in the original list. So, are the arguments passed by value or by reference still remains a mystery!
The answer is the arguments are passed neither by value nor by reference, instead python has its own unique way of passing arguments by assignment. The argument passed in is actually a reference to an object (but the reference is passed by value).
Everything in python is an object (even the classes we create), some objects are mutable while some are not. It’s this property of an object that decides how the value is changed when this object is passed as an argument to a function.
- If you pass a mutable object (like lists, sets, dictionaries, etc.) into a function, the function gets a reference to that same object and you can mutate it as per you desire, but if you rebind the reference in the function (i.e. assign the variable referring to the passed object a new value) nothing happens to the originally passed object but a new object is created and the variable now refers to it, the outer scope will know nothing about it, and after you’re done, the outer reference will still point at the original object.
- If you pass an immutable object (like strings, integers, tuples, etc.) to a function, you still can’t rebind the outer reference without using a prefix, and you can’t even mutate the object.