Sunday, May 8, 2022

Python - Default and Unlimited Arguments (Day 27)

This is a 100 Days challenge to learn a new language (Python). 100 Days of Code - The Complete Python Pro Bootcamp 

I will post some notes to motivate myself to finish this challenge.


Argument with Default Value



If some arguments are always the same in your custom function, then we can set those values as default.

Ex: Regular
# Define a function
def my_function(a, b, c):
    """Print input arguments"""
    print(a, b, c)

# Most of the cases, argument c is set to 0
my_function(a=1, b=2, c=0)
my_function(a=2, b=3, c=0)

Result:
1 2 0 2 3 0

Ex: Use Default Value
# Define a function
def my_function(a, b, c=0):
    """Print input arguments"""
    print(a, b, c)

# Most of the cases, argument c is set to 0
my_function(a=1, b=2)
my_function(a=2, b=3)

# If the argument c is not the default value, we can pass it
my_function(a=3, b=4, c=99)

Result:
1 2 0 2 3 0 3 4 99


Unlimited Positional Arguments



We define a function below.

Ex: 
# Define a function
def add(a, b):
    """Return the sum of input a and b"""
    return a + b

# Call custom function to get the sum of input
print(add(1, 2))

Result:
3

Then the add(a, b) function suits our needs if we only want to get the sum of two input numbers.

Later, imagine that if we need to get the sum of multiple input numbers (such as input a, b, c, and d), then we need to change this function definition.

In python, we can use unlimited positional arguments (*args) to allow you to pass multiple arguments.

Ex: 
# Define a function with *args
def my_function(*args):
    """Exp"""
    # Checking its type
    print("type of args", type(args))

    # Print this tuple value
    print("args: ", args)

    # Access tuple by index
    print("args[1]: ", args[1])

    # Loop through it
    print("Loop through all items")
    for num in args:
        print(num)

# Call custom function with 5 arguments
my_function(1, 2, 3, 4, 5)

# Call custom function with 5 arguments
my_function(2, 1, 3, 4, 5)


Result:
type of args <class 'tuple'> args: (1, 2, 3, 4, 5) args[1]: 2 Loop through all items 1 2 3 4 5
type of args <class 'tuple'> args: (2, 1, 3, 4, 5) args[1]: 1 Loop through all items 2 1 3 4 5

The type of *args is tuple, and we can use for loop to access its element.
And if we change the order of input arguments, then the result got changed since it is positional arguments.

Therefore, to utilize *args, our previous get sum example can be adjusted as the following.

Ex: 
# Define a function with *args
def add(*args):
    """Return the summary of multiple input"""
    sum_of_args = 0

    # Loop through input args
    for num in args:
        sum_of_args += num

    return sum_of_args

# Call custom function with 2 arguments
print(add(1, 2))

# Call custom function with 5 arguments
print(add(1, 2, 3, 4, 5))

Result:
3
15


Unlimited Keyword Arguments



In some cases, using index to access the unlimited positional arguments is not that convenient.

Then we can use Unlimited Keyword Arguments (**kwargs)

Ex: 
# Define a function with **kwargs
def my_function(**kwargs):
    """Exp"""
    # Checking its type
    print("type of kwargs", type(kwargs))

    # Print this dictionary value
    print("kwargs", kwargs)

    # Access dictionary by its key (key exists)
    print(f"key1: {kwargs['key1']}")

    # Access dictionary by its key with get function (key exists)
    print(f"key1: {kwargs.get('key1')}")

    # Access dictionary by its key with get function (key does not exist)
    # We can setup the default value if this key does not exist
    print(f"key3: {kwargs.get('key3', 0)}")

    # Loop through
    print("Loop through all items")
    for key, value in kwargs.items():
        print(key, value)

# Call custom function with 2 arguments
my_function(key1="value1", key2="value2")

Result:
type of kwargs <class 'dict'> kwargs {'key1': 'value1', 'key2': 'value2'} key1: value1 key1: value1 key3: 0 Loop through all items key1 value1 key2 value2

The type of **kwargs is dictionary, and we can use key instead of magic index number to access its value.
Also we can use for loop with items() to access all its key-value pair.

This is an example how we can use it in our calculation program.

Ex: 
# Define a function with **kwargs
def calculate(num, **kwargs):
    """Return the calculation of multiple input"""
    # Use get function and default value to access the dictionary element
    num += kwargs.get("add", 0)
    num -= kwargs.get("sub", 0)
    num *= kwargs.get("mul", 1)
    num /= kwargs.get("div", 1)

    return num

# Call custom function with 3 arguments
print("(1 + 1) * 2 = ", calculate(1, add=1, mul=2))

# Call custom function with 4 arguments
print("(1 + 6 - 4) * 8 / 3 = ", calculate(1, add=6, sub=4, mul=8, div=3))

Result:
(1 + 1) * 2 = 4.0 (1 + 6 - 4) * 8 / 3 = 8.0


Tkinter - The GUI Program




Ex: Hello World 
import tkinter as tk

# Callback function for tk.Button
def on_button_clicked():
    """Copy the content from my_entry to my_label"""
    my_label.config(text=my_entry.get())

# Initializes Tk and creates its associated Tcl interpreter
# It also creates a toplevel window, known as the root window,
# which serves as the main window of the application.
root = tk.Tk()

root.title("My First GUI Program")
root.minsize(width=500, height=300)

# Label
my_label = tk.Label(text="Hello Wordl!", font=("Arial", 24, "bold"))
my_label.pack()

# Entry
my_entry = tk.Entry()
my_entry.pack()

# Button
my_button = tk.Button(text="Click me", command=on_button_clicked)
my_button.pack()

# Start the Event Loop
root.mainloop()


Project - Miles to Kilometers Converter



Ex:
import tkinter as tk

# Callback function for tk.Button
def on_button_clicked():
    """Convert miles to kilometers and show it to km_value_label"""
    miles = float(miles_entry.get())
    km = miles * 1.609
    km_value_label.config(text=f"{km}")

# Initializes Tk and creates its associated Tcl interpreter
# It also creates a toplevel window, known as the root window,
# which serves as the main window of the application.
root = tk.Tk()

root.title("Converter")
root.config(padx=20, pady=20)
root.minsize(width=200, height=100)

# Entry
miles_entry = tk.Entry(width=20)
miles_entry.grid(column=1, row=0)

# Label
miles_label = tk.Label(text="Miles")
miles_label.grid(column=2, row=0)

desc_label = tk.Label(text="is equal to")
desc_label.grid(column=0, row=1)

km_value_label = tk.Label(text="0")
km_value_label.grid(column=1, row=1)

km_label = tk.Label(text="Km")
km_label.grid(column=2, row=1)

# Button
calculate_button = tk.Button(text="Calculate", command=on_button_clicked)
calculate_button.grid(column=1, row=2)

# Start the Event Loop
root.mainloop()

No comments:

Post a Comment