Default Parameter Values
Sometimes you want to describe some default behaviour for a function. This is where default parameter values come in. You may also hear them called "default arguments".
We've actually already seen an example of a default parameter value earlier in this section. Remember the print
function has a keyword only argument called sep
? What happens if we don't provide a value for it when calling print
?
print(1, 2, 3, 4, 5)
We get the following:
1 2 3 4 5
The values separated by spaces. That's because sep
has a default paramater value of ' '
. If we don't provide a value for sep
when calling print
, the print function falls back to this default value. The print
function actually takes several other keyword only arguments with default values, including end
, which defines some string to finish the print line with. By default, this value is '\n'
, which means "start a new line". This is why each print output is on a different line.
Defining default parameter values
So, how can we define our own default values?
It's actually quite simple. When defining the function, we can provide a default value for any parameter by writing =
followed by the default value.
def add(x, y=3):
sum = x + y
print(sum)
In the example above, the parameter y
has been given a default value of 3
. When calling the add
function, we can now provide either one or two arguments. If we provide one positional argument, that value is assigned to the parameter x
, and y
takes the defaul value 3
. If we provide two positional arguments, the value of y
is overwritten by the value of our second positional argument.
add(4) # 7
add(2, 6) # 8
Of course, we can still use keyword arguments as well, but we have to make sure that we don't leave any parameters unassigned.
add(x=3) # 6
add(x=5, y=2) # 7
add(y=2) # Error
In the final example, we never provided a value for x, so we get a TypeError
.
TypeError: add() missing 1 required positional argument: 'x'
The order of default parameters
One thing to be aware of when using default parameter values is that we have to be careful when using them in conjunction with non-default parameters.
All parameters with a default value must be placed after parameters without them. The following is not valid:
def add(x=2, y):
sum = x + y
print(sum)
When trying to run the code above, Python will raise a SyntaxError
.
SyntaxError: non-default argument follows default argument
Parameters with default values must be specified after parameters without them.
Pitfalls
While useful, default parameter values can introduce several hard to understand bugs into your code if you're not careful.
Using another variable as a default parameter value
Default parameter values don't have to be integers. You can use just about anything as a default value. If it can be passed in as an argument to a function, it's a valid default parameter value.
As we've seen, we can pass in variables as arguments. No problem. Our add
function provides the variable sum
as an argument to print
for example.
For regular function arguments this is totally fine, and in many cases encouraged. Variables allow us to use names to better identify what things actually are. It makes our code more readable. When using a variable for a default parameter value, however, things may not work as you expect.
Let's take a look at the following example.
default_y = 3
def add(x, y = default_y):
sum = x + y
print(sum)
add(2) # 5
default_y = 4
print(default_y) # 4
add(2) # 5
The comment next to the final line isn't a typo. The output of this second add
function is in fact 5
. But why? We redefined default_y
to be 4
. If we try to print default_y
, we get 4
, so we know the reassignment worked.
The reason is that default values are evaluated when a function is defined. When we defined the add
function, the value of default_y
was 3
, not 4
. By time we reassign default_y
, the add
function has already decided what the value of default_y
is.
Default paramater values are evaluated when a function is defined, not when it gets called.
Another problem with variables and default parameter values
Let's consider another example:
def add(x, y = default_y):
sum = x + y
print(sum)
default_y = 3
add(2) # Error
When trying to run this example, we get an error:
NameError: name 'default_y' is not defined
This example is meant to hammer home the idea that default parameter values are evaluated when a function is defined, not when it gets called.
When we define the add
function, we haven't get defined the default_y
variable. So when we try to use it as a default parameter value, Python doesn't know what we're talking about, and raises an error.
A final warning
Be careful when using a list or dictionary as a default parameter argument. Unlike integers, these values will update if you modify the original list or dictionary.
This is due to a language feature called mutability. It's not important to understand what this is at this point, but know that mutable values, like lists, behave differently to integers and strings behing the scenes when you change them.