Functions in python - args and kwargs

Earlier we saw how to write functions in python and how to call them in our program. For those functions, the number of inputs or arguments were defined. They took fixed number of positional or keyword arguments or had a default value assigned to one or more of the arguments. 

 But how to handle situations where we want to write a function wherein we do not know how many arguments we are going to give. In these conditions, the *args and **kwargs functionality is used.

We will first try to understand how each of these work.

*args

When we include *args in the definition of a function, it means that we can give it any number of keyword arguments to it.

To understand how *args work, we will make a function that concatenates any string arguments given to it.

But let’s do it stepwise. We will first see in what form the *args are interpreted inside the function. We will just make our first version of the function that prints out the type of the args object.

def add_str(*args):
    print(f'The "args" are read as {type(args)} type of object.')
add_str(2,3,4,5)
The "args" are read as <class 'tuple'> type of object.

We see above that the function combines all the positional arguments of the function under *args as tuple. This gives us the method with which to use them. Now we will modify this function that would concatenate the strings. If a number is present we will convert it to string and then concatenate.

To do this: - an empty string is created and each position argument is iterated over and added to the empty string. - we will use str() function to convert any numerical in the args. - str() function does not have any effect when given a string object as argument. So there is no need to check the type of the element in arg. - we will insert a space character after each arg added.

def add_str(*args):
    res = ''
    for arg in args:
        res = res + str(arg) + ' '
        
    return res
add_str('a', 'fg', 'htw', 'c', 4, 'g5', 68)
'a fg htw c 4 g5 68 '

In summary, the *args arguments in a function is interpreted as a tuple inside a functions. Each element of the tuple is the postional argument given to the function.

**kwargs

Now we will see how the **kwargs are interpreted inside a function in similar fation we did with *args.

Before that we must know that only keyword arguments can be passed under **kwargs.

def add_str2(**kwargs):
    print(f'The "kwargs" are read as {type(kwargs)} type of object.')
add_str2(a=2, b=4, c='teak', d = 'wood')
The "kwargs" are read as <class 'dict'> type of object.

So, the **kwargs are read as a dictionary in contrast with a tuple in case of *args.

Now, we will write a function that does the same thing of concatenating the number/strings given to the function.

def add_str2(**kwargs):
    res = ''
    for key in kwargs:
        res = res + str(kwargs[key]) + ' '
        
    return res
add_str2(a=2, b=4, c='teak', d = 'wood')
'2 4 teak wood '

*args and **kwargs can be used when a function can be given optional arguments.

For example, the pyplot.plot function has following syntax for calling:

matplotlib.pyplot.plot(*args, scalex=True, scaley=True, data=None, **kwargs)

You can see that the function takes regular keyword arguments which have default values, the *args and also **kwargs.

One example of its usage is:

plot(x, y, 'go--', linewidth=2, markersize=12)

Here, you can see that: - none of the regular keyword arguments is given while calling the function. So the default values for these keyword arguments will be taken by the function. - the arguments x, y and go-- will be taken by the function under *args. - the keyword arguments linewidth and markersize will be taken under **kwargs.

Reference: The matplotlib code was taken from its documentation page

Using exact names for *args and **kwarg is not necessary

We can use any name for *args and *kwargs. The only import thing is the * or **.

Single (*) as in *name will stand for positional arguments *args.

Double (**) as in **name will stand for the keyword arguments **kwargs.

Popular posts from this blog

Principal Coordinate analysis in R and python

Principal Coordinate Analysis (PCoA) in R