Functions
A function is a sequence of code that performs a task and can be easily reused. ♻️
We've already used functions in call expressions like:
abs(-100)
pow(2, 10)
A function takes in an input (the arguments) and returns an output (the return value).
-100 → abs → 100
In the abs
expression, there is a single argument of -100 and a return value of 100.
2, 10 → pow → 1024
In the pow
expression, there are two arguments of 2 and 10, and a return value of 1024.
Those are all functions provided by Python, however. Many times, we want to create our own functions, to perform some task unique to our program.
Defining functions
The most common way to define functions in Python is with a def
statement.
Here's the general template:
def ():
return
Here's an actual example:
def add_two(num1, num2):
return num1 + num2
Once defined, we can call the function, just like we call built-in Python functions:
add_two(2, 2)
add_two(18, 69)
Let's break down that function definition statement a little. The first line that declares the name and parameters is called the function signature, and all the indented lines below it are the function body.
def (): # ← Function signature
return # ← Function body
def add_two(num1, num2): # ← Function signature
return num1 + num2 # ← Function body
The Python language is somewhat unique in that it uses indentation to show how lines of code relate to each other. (Other languages use brackets or keywords). That means that the lines in the function body must be indented. It doesn't actually matter how much they're indented - heck, Python will let you get away with indenting them with 200 spaces! However, the standard convention is either 2 spaces or 4 spaces; enough indentation to be visible to someone reading the code, but not so much that lines of code become ridiculously long.
The function body can (and often does) have multiple lines:
def add_two(num1, num2): # ← Function signature
result = num1 + num2 # ← Function body
return result # ← Function body
Parameters vs. arguments
We've now used two different terms to refer to the values that get passed into a function: parameters and arguments. Well, which is it?? Both!
When we're defining a function, the parameters are the names given to the values that will eventually get passed into a function. The following function accepts two parameters, num1
and num2
, and the return value sums up those two parameters.
def add_two(num1, num2):
return num1 + num2
However, when we're actually calling that function, we describe the values passed in as the arguments. Below, we pass in two arguments of 18 and 69.
add_two(18, 69)
The difference might seem subtle and overly pedantic, and well, as it turns out, programmers can be pedantic sometimes. 😊
Return values
The return
keyword returns a value to whoever calls the function. After a return statement is executed, Python exits that function immediately, executing no further code in the function.
def add_two(num1, num2):
return num1 + num2
result = add_two(2, 4)
After running that code, the variable result
holds the return value, 6.
Just like we did with the built-in functions, we can use function calls in arithmetic expressions:
big_sum = add_two(200, 412) + add_two(312, 256)
And also nest calls inside other calls:
huge_sum = add(add(200, 412), add(312, 256))
Spot the bug! 🐞
There's something wrong with this code... do you see the problem?
def add_two(num1, num2):
return result
result = num1 + num2
result = add_two(2, 4)
Spot the bug! 🐛
Here's some more buggy code:
def add_two():
return num1 + num2
result = add_two(2, 4)
Spot the bug! 🦟
Here's the last bit of code that's problematic:
def add_two(num1, num2):
result = num1 + num2
result = add_two(2, 4)