11.07.2024

Tips and tricks for clean and readable Python code

Learning to program is a steep path. One side of learning includes learning how to code and the other side includes how to do it elegantly. For me that was the hardest part. I was able to solve many things using brute force and clumsily, but when it came time to write an elegant solution, no thanks, I will always use nested loops . But of course this doesn't work for several reasons as the code needs to be dry (not repeating), memory friendly and readable by other people. But Google was my friend and little by little I found tools that allowed me to more easily create more elegant solutions without having to reinvent the wheel. These are some of the built-in Python wizards that help make the code simpler and easier to read.

*args and **kwargs

*args and **kwargs help make functions generally usable. By using *args as a function parameter, the function can take any number of arguments. Without *args, integer and string arguments must be taken into account.

With *arguments:

And without that it just throws an error...

**kwargs has similar functionality to *args, but for key-value pairs. **kwargs can be used in a function that does not require counting or has an unknown number of key-value pairs .

List comprehension

List comprehensions allow developers to create single-line lists. Without using list comprehension, you can create a list of numbers using the following code:

A list comprehension converts this code into a single line. The basic syntax is:

[expression for item in iterable] and in simple code it looks like this:

List comprehensions can also include filtering functions.

Lists aren't the only data structure you can create this way. We can create a dictionary and define it using the same creation pattern. The basic syntax of the dictionary is:

{key_expression: value_expression for item in iterable} .

We can multiply any number in our number list by 10 in a by_tens dictionary.

We can also do this with a set. The basic syntax is

{expression for item in iterable} . The code looks like this:

Zipper()

zip() allows you to iterate through multiple lists at once and create tuples of matching elements. zip() shortens a potentially multi-line iteration to a single line of code.

zip() iterates the length of the smallest list. If the specified lists have different lengths, the tuples are only as long as the smallest list. The following code clearly illustrates the two points mentioned above:

Merge dictionaries

You can merge dictionaries using the update() function or the dictionary unpack syntax ( ** ).

Or you can use the update function to add the water_pets object to the land_pets object: land_pets.update(water_pets).

Chained comparison operators

Chaining comparison operators allows you to combine multiple comparisons into a single expression. Concatenation eliminates the need for the explicit "and" operator. This improves code readability and performance by reducing the number of different comparisons.

The following example compares miles variables to determine whether the distance is within range. Without chaining the comparison operators, the code looks like this:

When the comparison is expressed as a compound condition, it looks like this:

ternary operator

Ternary operators allow developers to write if conditions on a single line. The basic syntax is:

result = true_value if condition else false_value

If the condition evaluates to True , the expression returns the value True. If the condition evaluates False , the expression returns False. Below is an example without the spin operator:

Compared to the if condition with the ternary operator:

Decorators

Decorators modify functions without changing the source code. A decorator is a new function that takes the original function as an argument, uses a new function to modify it, and then returns the function with the updated functionality.

Let's start with a basic division function.

Division(10.5) returns 2

Division (9, 3) returns 3

For this example, let's assume that this function always needs to divide the larger number by the smaller number. There are many reasons why it would not be ideal to modify the source code, and in these cases a decorator is helpful. If you're familiar with closures, this will sound familiar. For those who don't know, decorator is a function that creates, modifies and returns a function. The decorator shell looks like this:

Inside the inner function, we check if the arguments are in the correct order and perform the necessary swaps (another Python trick) if they are not.

The inner function looks and behaves like any basis function.

Now there are different ways to use the decorator function to change the split function. The first way to do this is to use @decorator and it looks like this:

Another way to do this is to assign the function as a variable:

Happy coding!

These tips will definitely take your code from simple to elegant. The more you work with Python, the easier it becomes.

Created with Sketch.

Aucun commentaire:

Enregistrer un commentaire