Collect and spread
The stars in the def collect. The stars in the call spread. Notice the types printed for numbers and details.
*args lets a function accept any number of positional arguments (collected into a tuple), and **kwargs any number of keyword arguments (collected into a dict). The same stars in a call do the opposite: they spread a list or dict into separate arguments, which is how wrappers forward arguments unchanged.
Change the code and press Run (Ctrl+Enter). Predict what will happen first, then break it on purpose and read what changes. Your edits are saved and match the lesson page.
Ready for more? This phase has 6 hands-on exercises with automatic checks.
Practice questions
Write the code in the editor, run it, then open the model answer to compare.
Write average(*numbers) that returns the mean of any number of values, or 0 when none are given. Print average(2, 4, 9) and average().
Write make_url(host, **query) that returns https://host?key=value&key=value using all keyword arguments in order. Call make_url("example.com", page=2, sort="new").
Write call_twice(func, *args, **kwargs) that calls func two times with the same arguments and returns a list of both results. Test it with pow or max.
Explain it without notes
What do *args and **kwargs collect, and what types are they inside the function?
Explain what f(*items, **options) does in a call.
Why do wrapper functions take *args, **kwargs?
What is the order of the parameter kinds in a def line?
Expected output
numbers is () of type tuple
0
numbers is (1, 2, 3) of type tuple
6
details is {'name': 'Asha', 'age': 12} of type dict
numbers is (4, 5, 6) of type tuple
15
numbers is (4, 5, 6, 10, 20, 30) of type tuple
75
details is {'x': 1, 'y': 2, 'z': 3} of type dict