Functions in Python
Learning objectives
By the end of this pill you will be able to:
- define a function with
def; - distinguish between positional and keyword parameters;
- use optional parameters (default values);
- handle a variable number of arguments (
*argsand**kwargs).
Basic definition
A function is a reusable block of code that performs a specific action. In Python it is defined with the keyword def, followed by the name, parentheses and a colon. The function body must be indented.
def greet(name):
"""This function prints a greeting."""
message = f"Hello, {name}!"
return message
# Function call
result = greet("Mario")
print(result) # Hello, Mario!
Positional and keyword parameters
When calling a function you can pass arguments in two ways:
- Positional: order matters. The first value goes to the first parameter, the second to the second, etc.
- Keyword: you specify the parameter name. Order no longer matters.
def describe(animal, sound):
print(f"The {animal} goes {sound}")
# Positional (correct order)
describe("dog", "woof")
# Keyword (order irrelevant)
describe(sound="meow", animal="cat")
# Mixed (positional must come before keyword!)
describe("cow", sound="moo")
Optional parameters (defaults)
You can assign a default value to a parameter. If the caller does not supply that value, the default is used. Parameters with defaults must always be defined after those without.
# 'exponent' is optional, default = 2
def power(base, exponent=2):
return base ** exponent
print(power(3)) # 3^2 = 9 (uses the default)
print(power(3, 3)) # 3^3 = 27 (overrides the default)
Note: Be careful with mutable default values (such as lists or dictionaries). They are created only once when the function is defined.
Variable number of arguments
Sometimes you don’t know in advance how many arguments will be passed. Python provides two powerful tools for this.
*args: tuple of positional arguments
The asterisk * before the parameter name collects all extra positional arguments into a tuple.
def sum_all(*numbers):
# 'numbers' is a tuple: (10, 20, 30)
total = 0
for n in numbers:
total += n
return total
print(sum_all(10, 20, 30)) # 60
**kwargs: dictionary of keyword arguments
The double asterisk ** collects extra keyword arguments into a dictionary (Keyword ARGS).
def create_profile(name, **details):
# 'details' is a dictionary: {'age': 18, 'city': 'Rome'}
print(f"Profile of {name}:")
for key, value in details.items():
print(f" - {key}: {value}")
create_profile("Luca", age=18, city="Rome", sport="Football")
Argument unpacking
You can also do the reverse: if you have a list or tuple and want to pass its values as separate arguments, use *.
coordinates = (10, 20)
def draw_point(x, y):
print(f"Drawing point at {x}, {y}")
# Unpacking: the tuple is 'expanded' into the two arguments
draw_point(*coordinates)
In brief: use optional parameters to simplify common calls, and *args/**kwargs to make your functions flexible and capable of handling unexpected input.
EC