Python Arena
Step 4 of 4

Any number of arguments

print takes any number of arguments: print("a"), print("a", "b", "c"), even print(). Your own functions can do the same. A star * before a parameter's name collects all the remaining arguments of a call into a tuple:

def total(*numbers):
    print("Got", len(numbers), "numbers:", numbers)
    return sum(numbers)


print(total(1, 2, 3))
print(total(10))
print(total())
Output
Got 3 numbers: (1, 2, 3)
6
Got 1 numbers: (10,)
10
Got 0 numbers: ()
0

Inside the function, numbers is an ordinary tuple: you can loop over it, index it and take its length. (A tuple with one item is printed with a comma, (10,), to tell it apart from a number in parentheses.) When no better name fits, such a parameter is usually called *args, short for arguments.

With ordinary parameters

Ordinary parameters can come before the starred one. They take the first arguments, and the starred one gets all the rest, which may be none at all:

def report(title, *scores):
    print(title)
    for score in scores:
        print("-", score)


report("Round 1", 7, 9, 4)
report("Round 2")
Output
Round 1
- 7
- 9
- 4
Round 2

A list is one argument

A list given to such a function is still one argument, not many. Here numbers becomes a tuple with one item, the list, and sum can't add a list to a number:

def total(*numbers):
    return sum(numbers)


values = [1, 2, 3]
print(total(values))
Python stops with
Traceback (most recent call last):
  File "main.py", line 6, in <module>
    print(total(values))
          ~~~~~^^^^^^^^
  File "main.py", line 2, in total
    return sum(numbers)
TypeError: unsupported operand type(s) for +: 'int' and 'list'

A star in the call spreads the list out into separate arguments: total(*values) is the same as total(1, 2, 3), and returns 6.

Your task

Challenge 1 of 3

Fill in the blank so that longest accepts any number of words, and the program prints giraffe.

Challenge 2

Write a function average(*numbers) that returns the mean of any number of numbers, or 0.0 when it gets none. average(1, 2, 3, 4) returns 2.5.

Challenge 3

Write a function shopping_list(title, *items) that prints the title with a colon and then the items, numbered from 1. With no items at all, it prints the title and : nothing to buy on one line instead. shopping_list("Groceries", "milk", "eggs", "bread") prints:

Groceries:
1. milk
2. eggs
3. bread