<?xml version="1.0" encoding="UTF-8"?>
<rss version="2.0" xmlns:atom="http://www.w3.org/2005/Atom" xmlns:dc="http://purl.org/dc/elements/1.1/">
  <channel>
    <title>DEV Community: Favour George</title>
    <description>The latest articles on DEV Community by Favour George (@psycode99).</description>
    <link>https://dev.to/psycode99</link>
    <image>
      <url>https://media2.dev.to/dynamic/image/width=90,height=90,fit=cover,gravity=auto,format=auto/https:%2F%2Fdev-to-uploads.s3.amazonaws.com%2Fuploads%2Fuser%2Fprofile_image%2F959992%2Fbbe734ea-b394-4fb3-95ec-95d19f09c1cb.jpg</url>
      <title>DEV Community: Favour George</title>
      <link>https://dev.to/psycode99</link>
    </image>
    <atom:link rel="self" type="application/rss+xml" href="https://dev.to/feed/psycode99"/>
    <language>en</language>
    <item>
      <title>Python’s Assert Statement: A Not-So Comprehensive Guide</title>
      <dc:creator>Favour George</dc:creator>
      <pubDate>Sun, 03 Sep 2023 02:05:34 +0000</pubDate>
      <link>https://dev.to/psycode99/pythons-assert-statement-a-not-so-comprehensive-guide-1dlc</link>
      <guid>https://dev.to/psycode99/pythons-assert-statement-a-not-so-comprehensive-guide-1dlc</guid>
      <description>&lt;h1&gt;
  
  
  &lt;strong&gt;What are Assertions?&lt;/strong&gt;
&lt;/h1&gt;

&lt;p&gt;Assertions are statements used to prove that a certain condition is true or has stayed true. If the condition proves to be false then the program will generally raise an AssertionError.&lt;/p&gt;

&lt;h1&gt;
  
  
  &lt;strong&gt;When to use Assertions&lt;/strong&gt;
&lt;/h1&gt;

&lt;p&gt;As powerful as assertions can be, they shouldn't be used haphazardly in your code as this could result in quite a mess especially when they are in a production environment, Ill explain this later. For now, the key point is that assertions are mainly used as a debugging aid to test conditions.&lt;/p&gt;

&lt;h1&gt;
  
  
  &lt;strong&gt;Assertion Syntax&lt;/strong&gt;
&lt;/h1&gt;

&lt;p&gt;The Python &lt;em&gt;assert&lt;/em&gt; statement mainly consists of the &lt;em&gt;assert&lt;/em&gt; keyword, the condition to test for and an optional assertion message to be returned if the condition proves to be false. This syntax is shown below:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight python"&gt;&lt;code&gt;&lt;span class="n"&gt;odds&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="mi"&gt;4&lt;/span&gt;
&lt;span class="k"&gt;assert&lt;/span&gt; &lt;span class="n"&gt;odds&lt;/span&gt; &lt;span class="o"&gt;&amp;lt;&lt;/span&gt; &lt;span class="mi"&gt;3&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="s"&gt;'odds less than 3 is required'&lt;/span&gt;

&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;If the condition evaluates to be true, then the program continues its execution as usual, otherwise, if it evaluates to be false, then it returns an AssertionError. The &lt;em&gt;assert_message&lt;/em&gt; parameter though optional, is quite handy in providing a good description of the problem.&lt;/p&gt;

&lt;h1&gt;
  
  
  &lt;strong&gt;Common Assertion Types&lt;/strong&gt;
&lt;/h1&gt;

&lt;p&gt;Lets look at some of the commonly used assertion types in this section. There are various assertion types but for this article, well focus on three of the most common types:&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;
&lt;strong&gt;Integrity/Identity Assertion:&lt;/strong&gt; This type of assertion is used to test for an entity's identity thus proving its integrity. It checks for the data type of the entity in the assertion
&lt;/li&gt;
&lt;/ul&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight python"&gt;&lt;code&gt;&lt;span class="n"&gt;a&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="mi"&gt;1&lt;/span&gt;
  &lt;span class="n"&gt;b&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="mi"&gt;2&lt;/span&gt;
  &lt;span class="k"&gt;assert&lt;/span&gt; &lt;span class="n"&gt;a&lt;/span&gt; &lt;span class="ow"&gt;is&lt;/span&gt; &lt;span class="n"&gt;a&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;ul&gt;
&lt;li&gt;
&lt;strong&gt;Association Assertion:&lt;/strong&gt; This type of assertion is used to check if an entity is associated in any way with a given collection such as a list, set, tuple etc. It checks if the item is a member of that collection
&lt;/li&gt;
&lt;/ul&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight python"&gt;&lt;code&gt;&lt;span class="k"&gt;def&lt;/span&gt; &lt;span class="nf"&gt;checker&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;fruit&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;fruits&lt;/span&gt;&lt;span class="p"&gt;):&lt;/span&gt;
      &lt;span class="k"&gt;assert&lt;/span&gt; &lt;span class="n"&gt;fruit&lt;/span&gt; &lt;span class="ow"&gt;in&lt;/span&gt; &lt;span class="n"&gt;fruits&lt;/span&gt;
      &lt;span class="k"&gt;return&lt;/span&gt; &lt;span class="bp"&gt;True&lt;/span&gt;

  &lt;span class="n"&gt;checker&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="s"&gt;'apple'&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="p"&gt;[&lt;/span&gt;&lt;span class="s"&gt;'apple'&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="s"&gt;'banana'&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="s"&gt;'cherry'&lt;/span&gt;&lt;span class="p"&gt;])&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;ul&gt;
&lt;li&gt;
&lt;strong&gt;Comparison:&lt;/strong&gt; This type of assertion is used to compare two or more values
&lt;/li&gt;
&lt;/ul&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight python"&gt;&lt;code&gt;    &lt;span class="k"&gt;assert&lt;/span&gt; &lt;span class="mi"&gt;5&lt;/span&gt; &lt;span class="o"&gt;&amp;gt;&lt;/span&gt; &lt;span class="mi"&gt;3&lt;/span&gt;

&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;h1&gt;
  
  
  &lt;strong&gt;Limitations of Assertions&lt;/strong&gt;
&lt;/h1&gt;

&lt;p&gt;As I mentioned earlier, assertions are quite powerful but when used randomly can lead one into a pitfall. To avoid this, it is quite necessary to know the limitations of assertions and under what conditions not to use them.&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;&lt;p&gt;&lt;strong&gt;Data Validation:&lt;/strong&gt; Assertions shouldn't be used to validate data or user input because assertions can be disabled globally thus resulting in unexpected results as well see in the code below:&lt;/p&gt;&lt;/li&gt;
&lt;li&gt;&lt;p&gt;&lt;strong&gt;Exception Handling:&lt;/strong&gt; Assertions shouldn't be used as substitutes to proper exception handling in your code for the same reasons they shouldn't be used for data validation because they can be disabled.&lt;/p&gt;&lt;/li&gt;
&lt;/ul&gt;

&lt;p&gt;Summarily, assertions are powerful debugging tools or aids. However, their usage should be done meticulously to avoid falling into one of its pitfalls&lt;/p&gt;

&lt;p&gt;That's it for this article, Thanks for reading and don't break production with your assertion.&lt;/p&gt;

</description>
    </item>
    <item>
      <title>Python's Prototype Design Pattern: Crafting Objects for Performance</title>
      <dc:creator>Favour George</dc:creator>
      <pubDate>Wed, 09 Aug 2023 21:44:12 +0000</pubDate>
      <link>https://dev.to/psycode99/pythons-prototype-design-pattern-crafting-objects-for-performance-2bl3</link>
      <guid>https://dev.to/psycode99/pythons-prototype-design-pattern-crafting-objects-for-performance-2bl3</guid>
      <description>&lt;p&gt;In a previous article, we discussed the singleton design pattern and saw how it could be applied in practice. In this article, well be discussing the prototype design pattern, when to use it and how to use it.&lt;/p&gt;

&lt;p&gt;The prototype design pattern lets you as a developer copy existing objects without making your code dependent on the classes in which they were instantiated from. So what does this mean? Say you had an object in your code and for some reason you wanted to create an exact copy of that object with its attributes, normally you would first create an object of the same class and then go through all the properties of the original object and copy over their values to the new object. However, it is important to note that not all objects can be copied that way because some of the objects properties (i.e. attributes and methods) may be private. Furthermore, you would have to know the objects class to create a duplicate and in a long codebase, this could become very tedious and this is where the prototype design pattern comes in.&lt;/p&gt;

&lt;p&gt;Fundamentally, the prototype pattern is just a &lt;em&gt;clone()&lt;/em&gt; function that accepts an object as an argument and returns a clone of the object.&lt;/p&gt;

&lt;h1&gt;
  
  
  Building a Prototype Design
&lt;/h1&gt;

&lt;p&gt;Let us implement the prototype design in code as follows::&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;from abc import ABCMeta, abstractmethod
from copy import deepcopy

# prototype interface
class Prototype(metaclass=ABCMeta):
    @abstractmethod
    def clone(self):
        pass

# concrete prototype
class Car(Prototype):
    def __init__ (self, make, model, year) -&amp;gt; None:
        self.make = make
        self.model = model
        self.year = year

    def clone(self):
        return deepcopy(self)

# client
car_1 = Car('Dodge', 'Challenger SRT', 2021)
cloned_car = car_1.clone()

print(car_1)
print(cloned_car)
print(car_1 == cloned_car)

&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;In the code above, we first import the necessary tools well need. We imported the &lt;strong&gt;&lt;em&gt;ABCMeta&lt;/em&gt;&lt;/strong&gt; class and &lt;strong&gt;&lt;em&gt;abstractmethod&lt;/em&gt;&lt;/strong&gt; decorator from the &lt;strong&gt;&lt;em&gt;abc&lt;/em&gt;&lt;/strong&gt; module. The ABCMeta class is used to define an abstract base class and the &lt;strong&gt;&lt;em&gt;abstractmethod&lt;/em&gt;&lt;/strong&gt; decorator is used to declare abstract methods that must be implemented by subclasses. We also imported the &lt;strong&gt;&lt;em&gt;deepcopy&lt;/em&gt;&lt;/strong&gt; function from the copy module. This function creates a deep copy of an object&lt;/p&gt;

&lt;h1&gt;
  
  
  Abstract Class
&lt;/h1&gt;

&lt;p&gt;This is a class that cannot be instantiated directly and is meant to be subclassed by other classes.&lt;/p&gt;

&lt;h1&gt;
  
  
  Abstract Method
&lt;/h1&gt;

&lt;p&gt;This is a method declared in abstract base classes but does not contain any implementation in the base class itself.&lt;/p&gt;

&lt;p&gt;We then created a class &lt;strong&gt;&lt;em&gt;Prototype&lt;/em&gt;&lt;/strong&gt; , that serves as the interface for creating prototype objects. The &lt;strong&gt;&lt;em&gt;metaclass=ABCMeta&lt;/em&gt;&lt;/strong&gt; argument specifies that this class is an abstract class (i.e. a class that cannot be instantiated directly and is meant to be subclassed by other classes) and should be treated as such.&lt;/p&gt;

&lt;p&gt;The &lt;strong&gt;&lt;em&gt;@abstractmethod&lt;/em&gt;&lt;/strong&gt; decorator marks the &lt;strong&gt;&lt;em&gt;clone&lt;/em&gt;&lt;/strong&gt; method as an abstract method. Abstract methods are declared in abstract base classes but do not contain any implementation in the base class itself. Subclasses inheriting from this base class are required to provide an implementation for this method&lt;/p&gt;

&lt;p&gt;We then created another class, &lt;strong&gt;&lt;em&gt;Car&lt;/em&gt;&lt;/strong&gt; , which implements our &lt;strong&gt;&lt;em&gt;Prototype&lt;/em&gt;&lt;/strong&gt; base class. We created a constructor method that is to be initialized when objects are created from the class. We then defined the implementation of our abstract method &lt;strong&gt;&lt;em&gt;clone&lt;/em&gt;&lt;/strong&gt; , derived from the Prototype class implemented in our car class. The clone function takes the object as an argument and returns a deep copy of the object.&lt;/p&gt;

&lt;p&gt;To test our code, we created a car object from the &lt;strong&gt;&lt;em&gt;Car&lt;/em&gt;&lt;/strong&gt; class, specifying all the needed attributes (make, model, year) and we named this object &lt;strong&gt;&lt;em&gt;car_1&lt;/em&gt;&lt;/strong&gt;. We then created another object, &lt;strong&gt;&lt;em&gt;cloned_car&lt;/em&gt;&lt;/strong&gt; , which is a clone of our first car, thanks to applying the clone method to our &lt;strong&gt;&lt;em&gt;car_1&lt;/em&gt;&lt;/strong&gt; object.&lt;/p&gt;

&lt;p&gt;Using our print statements, we can see they are not stored in the same memory address and they are not the same although one is a clone of the other as seen in the output below:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;&amp;lt; __main__.Car object at 0x000000FF942AE2E0&amp;gt;
&amp;lt; __main__.Car object at 0x000000FF94327040&amp;gt;
False

&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;h1&gt;
  
  
  Applications of the Prototype Design
&lt;/h1&gt;

&lt;p&gt;The prototype design is useful for:&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;&lt;p&gt;&lt;strong&gt;Reducing Object Creation Overload:&lt;/strong&gt; If object creation is a computationally expensive task, using the prototype design pattern can be more efficient than creating objects from scratch.&lt;/p&gt;&lt;/li&gt;
&lt;li&gt;&lt;p&gt;&lt;strong&gt;Creating Stateful Objects:&lt;/strong&gt; Prototypes can be used to capture the state of an object at a certain point in time, making it useful for tasks such as creating snapshots and the redo/undo functionality.&lt;/p&gt;&lt;/li&gt;
&lt;li&gt;&lt;p&gt;&lt;strong&gt;Dynamically Creating Objects:&lt;/strong&gt; In cases where the exact class of an object isnt known until runtime, the prototype pattern can be helpful to achieve runtime object creation without knowing the specific classes in advance&lt;/p&gt;&lt;/li&gt;
&lt;/ul&gt;

&lt;p&gt;With all that said, the keypoint is to understand that the prototype design pattern basically creates a clone of an existing object.&lt;/p&gt;

&lt;p&gt;Thats it for this article folks, dont just read it but also try to understand and perhaps even use it. So till next time, as usual, dont break production.&lt;/p&gt;

</description>
    </item>
    <item>
      <title>Singleton Design Pattern: Mastering the Art of Single Instance Classes</title>
      <dc:creator>Favour George</dc:creator>
      <pubDate>Mon, 07 Aug 2023 20:57:11 +0000</pubDate>
      <link>https://dev.to/psycode99/singleton-design-pattern-mastering-the-art-of-single-instance-classes-1d0i</link>
      <guid>https://dev.to/psycode99/singleton-design-pattern-mastering-the-art-of-single-instance-classes-1d0i</guid>
      <description>&lt;h1&gt;
  
  
  What are Design Patterns?
&lt;/h1&gt;

&lt;p&gt;A design pattern is a reusable solution to a general obstacle faced by developers while designing and building software. They are models or blueprints for solving recurring problems in software development&lt;/p&gt;

&lt;h1&gt;
  
  
  Why are Design Patterns necessary?
&lt;/h1&gt;

&lt;p&gt;Design patterns when used properly for the right problems can accelerate the speed of software development by helping developers to avoid reinventing the solution to an already solved problem. With that said, it is important to understand that design patterns are not an alternative to sound logic and problem-solving skills and as such, they shouldnt be used randomly and the developer should know under what circumstances a certain design pattern(s) should be used&lt;/p&gt;

&lt;p&gt;In the next few weeks, Ill be uploading articles on various design patterns. For today, lets get started with the singleton design pattern.&lt;/p&gt;

&lt;h1&gt;
  
  
  Singleton Design Pattern
&lt;/h1&gt;

&lt;p&gt;The singleton design pattern is a software design pattern that aims at making sure theres just one instance of a class in a program regardless of how many times an object is instantiated from said class.&lt;/p&gt;

&lt;p&gt;To show the singleton design pattern in practice, well use it to build a logger for logging errors into a log file. In a previous article &lt;a href="https://hashnode.com/post/clkzyk4jf000009mahkp97y6e"&gt;here&lt;/a&gt;, we built a logger but had an issue where we always had to specify the name of the log file as an argument in our logger function as shown below:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;import datetime

def logger(level, msg, logger):
    date = datetime.datetime.now()
    with open(f'./{logger}.log', 'a') as logger:
        logger.write(f'\n [{level}] {msg} ---- {date}'.format())

&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;This could result in quite a messy file structure as we could end up logging into multiple log files which wont be clean. So using the singleton design pattern, well create one and only one instance of our logger, logging all the messages to one log file that wont need to be provided as an argument when creating an object from our class. Lets get started.&lt;/p&gt;

&lt;p&gt;In the previous article where we built our logger &lt;a href="https://hashnode.com/post/clkzyk4jf000009mahkp97y6e"&gt;here&lt;/a&gt;, we created a &lt;a href="http://logger.py"&gt;logger.py&lt;/a&gt; file where we stored the code for our logger. Now we are going to modify that file by creating a class that logs to just one file. To implement the singleton design pattern, well create a dunder method or special method ( these are Python methods that are identified by two trailing underscores before and after their names ). This method is responsible for creating a new instance of a class if none exists as shown below&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;import datetime

class Logger():
    instance = None

    def __new__ (cls):
        if cls.instance == None:
            cls.instance = super(). __new__ (cls)
        return cls.instance

&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;In the code above, we import the datetime module to keep track of the time a message is being logged to our log file. We then created a class- Logger, we created a variable, instance, which shows if an instance of the class exists, for now, we set it to None. We then set up the dunder method, &lt;strong&gt;new&lt;/strong&gt; , which is responsible for creating a new instance of a class if none exists. This method takes a default argument, &lt;strong&gt;&lt;em&gt;cls&lt;/em&gt;&lt;/strong&gt; , which is a reference to the class itself (i.e. Logger ) and not an instance of the class as most would think. In the method, we then write an if statement to check if theres no instance of the class and if theres none, it creates one and then returns that instance. Likewise, if theres already an instance, it returns that instance.&lt;/p&gt;

&lt;p&gt;With that out of the way, let's create a method in the class for writing messages to our log file as shown:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;def __init__ (self) -&amp;gt; None:
        self.filename = "pyLogger.log"

    def log(self, level, msg):
        date = datetime.datetime.now()
        with open(self.filename, 'a') as logger:
            logger.write(f"[{level}] ---- {msg} ---- {date}\n")

&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;In the code above, we create a constructor method for our class which will automatically be called when an object is instantiated from the class and explicitly set a filename for our logger; this is where our logged messages will be written. Its important to note that we didnt pass the filename as an argument.&lt;/p&gt;

&lt;p&gt;We then wrote a method for writing logged messages into our log file, taking the level of the message (e.g. ERROR, CRITICAL, DEBUG etc ) and the message itself as arguments. We then set up the date, and write to our log file the level and message.&lt;/p&gt;

&lt;p&gt;To test if our singleton has been successfully implemented, well use the Logger class in a new file - &lt;a href="http://main.py"&gt;main.py&lt;/a&gt; as shown below:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;from logger import Logger

logger_1 = Logger()
logger_2 = Logger()

print(logger_1 == logger_2)
print(logger_1)
print(logger_2)

&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;In the code above, we import the Logger class from our &lt;a href="http://logger.py"&gt;logger.py&lt;/a&gt; file into our &lt;a href="http://main.py"&gt;main.py&lt;/a&gt; file. We then created two objects from the class, and heres the tricky part, normally these would be two different instances of the class and these two instances would be stored in different memory addresses but since we had implemented the singleton design pattern, these two instances are just one and are stored in the same memory address as shown below from the output of the code above.&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;True
&amp;lt;logger.Logger object at 0x00000071F1397940&amp;gt;
&amp;lt;logger.Logger object at 0x00000071F1397940&amp;gt;

&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;Now to use it in our logger, in our &lt;a href="http://main.py"&gt;main.py&lt;/a&gt; well keep the import of the Logger class and create an instance of it. Then well write a basic script, the same as we did in the &lt;a href="https://hashnode.com/post/clkzyk4jf000009mahkp97y6e"&gt;previous article&lt;/a&gt; on creating a logger, in the script well try to divide a number by zero and catch the Zero Division error that occurs and then log it to our logger as shown:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;from logger import Logger

logger_1 = Logger()

try:
    calc = 5 / 0
except ZeroDivisionError as err:
    logger_1.log("ERROR", err)
finally:
    print('done')

&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;If the code above runs successfully, our logger object would have created a logger file with the name we set it to in the class in our &lt;a href="http://logger.py"&gt;logger.py&lt;/a&gt; file and in the file you should see something like this:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;[ERROR] ---- division by zero ---- 2023-08-07 08:49:07.513796

&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;Alright folks, thats it for this article, weve learnt about the singleton design pattern and showed it in practice by building a logger. So to recap, the singleton design pattern is useful when we want to create just one instance of a class regardless of how many objects are instantiated from the class.&lt;/p&gt;

&lt;p&gt;So till next time nerds, dont break production.&lt;/p&gt;

&lt;p&gt;Your employer wont be happy 😀&lt;/p&gt;

</description>
    </item>
    <item>
      <title>Harness the Potential of Logging: Create a Python Logger from Scratch</title>
      <dc:creator>Favour George</dc:creator>
      <pubDate>Sun, 06 Aug 2023 21:30:54 +0000</pubDate>
      <link>https://dev.to/psycode99/harness-the-potential-of-logging-create-a-python-logger-from-scratch-6dg</link>
      <guid>https://dev.to/psycode99/harness-the-potential-of-logging-create-a-python-logger-from-scratch-6dg</guid>
      <description>&lt;p&gt;Imagine building an application for a client and it worked successfully on your computer and also worked successfully for the client initially. Then on a fateful morning, you get a message from the client saying the application is bugging out. To debug the error on the application, you have to replicate the error and that wont be an easy job if you dont know the steps the client had taken that led to this error occurring. This is where logging and loggers come in.&lt;/p&gt;

&lt;h1&gt;
  
  
  What is Logging?
&lt;/h1&gt;

&lt;p&gt;Logging is the process of keeping track of events occurring in your software to keep an eye out for possible bugs that survived the development phase and snuck themselves into production. Not just bugs can be tracked using logging but also how a user is using the program.&lt;/p&gt;

&lt;h1&gt;
  
  
  What is a Logger?
&lt;/h1&gt;

&lt;p&gt;A logger is a program that creates a logging file (.log) that enables developers to write to the file errors caught during development and production. Not only error messages could be written to the file, but warnings and information could also be written to the file to help developers keep track of how their programs are being used.&lt;/p&gt;

&lt;h1&gt;
  
  
  Why Loggers?
&lt;/h1&gt;

&lt;p&gt;Loggers are quite useful when code has been pushed into production and you cant keep track of the events occurring by simply printing to the console as you would do during development. In such a case, loggers are useful for keeping track of events occurring in the application and you can easily access the log file and see whats going on. Summarily, instead of littering your code with loads of print statements, you can simply write the message to the log file. This achieves two things: first, it keeps your codebase clean and second, it provides persistency ( i.e unlike the console that gets cleared every time the program is run, the log file is persistent. It's like the difference between storing things in a list and a database )&lt;/p&gt;

&lt;p&gt;Now Python has a default logger module, but for this article, well build a rudimentary version of the logger. If you would like a complete tutorial on the Python Logger module, indicate in the comments. Alright, lets get started.&lt;/p&gt;

&lt;h1&gt;
  
  
  Building a Logger
&lt;/h1&gt;

&lt;p&gt;Our logger is going to be able to log messages of 5 levels - Error, Warning, Critical, Info and Debug.&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;import datetime

def error(msg):
    date = datetime.datetime.now()
    with open('./logger.log', 'a') as logger:
        logger.write(f'\n [ERROR] {msg} ---- {date}'.format())

&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;In the code above, we create a &lt;a href="http://logger.py"&gt;logger.py&lt;/a&gt; file where well be writing the code for our logger. In our &lt;a href="http://logger.py"&gt;logger.py&lt;/a&gt; file, we first import the datetime module to help us keep track of the time in which each log is made to our log file. We then create a function error, that takes the message we wish to log to our log file as an argument. In the function, we set up the date, which is the time the user calls the function and then we open a logger.log file in append mode, meaning we write to the end of the file without altering its previous contents. We then write to the file the message, which was passed in as an argument as well as the date which was created earlier.&lt;/p&gt;

&lt;p&gt;We then copy the function and paste it four times, changing its name to the different levels we specified at the beginning of this section as shown&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;
def critical(msg):
    date = datetime.datetime.now()
    with open('./logger.log', 'a') as logger:
        logger.write(f'\n [CRITICAL] {msg} ---- {date}'.format())

def warning(msg):
    date = datetime.datetime.now()
    with open('./logger.log', 'a') as logger:
        logger.write(f'\n [WARNING] {msg} ---- {date}'.format())

def info(msg):
    date = datetime.datetime.now()
    with open('./logger.log', 'a') as logger:
        logger.write(f'\n [INFO] {msg} ---- {date}'.format())

def debug(msg):
    date = datetime.datetime.now()
    with open('./logger.log', 'a') as logger:
        logger.write(f'\n [DEBUG] {msg} ---- {date}'.format())

&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;Now to use our logger, we create a new Python file - &lt;a href="http://main.py"&gt;main.py&lt;/a&gt; and import our logger file into it. Now for testing purposes, well write a basic script to divide a number by zero and try catching the error (ZeroDivisionError) that comes up and then log it to our &lt;a href="http://logger.as"&gt;logger as&lt;/a&gt; shown below.:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;import logger

try:
    calc = 5 / 0
except ZeroDivisionError as err:
    logger.error(err)
finally:
    print('done')

&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;Now to see our logged message, we open the logger.log file and you should see this&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;
 [ERROR] division by zero ---- 2023-08-06 08:45:42.013959

&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;You can try the other functions we defined in the &lt;a href="http://logger.py"&gt;logger.py&lt;/a&gt; file such as critical at your leisure.&lt;/p&gt;

&lt;h2&gt;
  
  
  Simplifying Our Code
&lt;/h2&gt;

&lt;p&gt;In programming, theres a principle known as DRY ( Dont Repeat Yourself ) and its pretty... DRY.&lt;/p&gt;

&lt;p&gt;If you are a geek for code efficiency and minimalism, youd notice that our &lt;a href="http://logger.py"&gt;logger.py&lt;/a&gt; file is quite repetitive. We can create one function that takes the level, message and logger as arguments as shown below:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;import datetime

def logger(level, msg, log_file):
    date = datetime.datetime.now()
    with open(f'./{log_file}.log', 'a') as logger:
        logger.write(f'\n [{level}] {msg} ---- {date}'.format())

&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;The problem with this design is that every time we call the function, we have to explicitly provide the name of the log file we intend to use and it could become quite messy as we could be logging into multiple log files.&lt;/p&gt;

&lt;p&gt;To make this project even better we could implement the singleton design pattern to our logger, now thats for another article.&lt;/p&gt;

&lt;p&gt;So for now, weve built and used a basic Python logger, all praise to Mad Max.&lt;/p&gt;

&lt;p&gt;Thats it for now, Ill be uploading a new tutorial on how to implement the singleton design pattern to our logger later on. Till then, dont break production.&lt;/p&gt;

</description>
    </item>
    <item>
      <title>Python Itertools: Mastering Efficient Iteration for Enhanced Productivity</title>
      <dc:creator>Favour George</dc:creator>
      <pubDate>Tue, 25 Jul 2023 06:39:26 +0000</pubDate>
      <link>https://dev.to/psycode99/python-itertools-mastering-efficient-iteration-for-enhanced-productivity-2l86</link>
      <guid>https://dev.to/psycode99/python-itertools-mastering-efficient-iteration-for-enhanced-productivity-2l86</guid>
      <description>&lt;h1&gt;
  
  
  What is Itertools?
&lt;/h1&gt;

&lt;p&gt;Itertools is a Python module used for iterating over iterable data structures using a for loop. It is a collection of tools for handling iterators and iterations in a fast and memory-efficient way.&lt;/p&gt;

&lt;p&gt;Now, before we get started exploring the itertools module, lets understand a few important terms used in iteration.&lt;/p&gt;

&lt;h1&gt;
  
  
  Iterables
&lt;/h1&gt;

&lt;p&gt;An iterable is any data structure that can be iterated or looped over to access its individual items. Examples of iterables in Python include Lists, Tuples, Sets, Strings, Dictionaries etc.&lt;/p&gt;

&lt;h1&gt;
  
  
  Iterator
&lt;/h1&gt;

&lt;p&gt;An iterator is an object that allows you to traverse or move through elements of an iterable one at a time. Iterators are stateful, meaning that they maintain an internal state to keep track of their current position during iteration.&lt;/p&gt;

&lt;p&gt;Now with that out of the way, lets explore the various tools available to us through Itertools&lt;/p&gt;

&lt;h1&gt;
  
  
  Types of Iterators in Itertools
&lt;/h1&gt;

&lt;p&gt;There are mainly three types of iterators available to us in Itertools:&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;&lt;p&gt;Infinite Iterators&lt;/p&gt;&lt;/li&gt;
&lt;li&gt;&lt;p&gt;Finite Iterators&lt;/p&gt;&lt;/li&gt;
&lt;li&gt;&lt;p&gt;Combinatoric iterators&lt;/p&gt;&lt;/li&gt;
&lt;/ul&gt;

&lt;h2&gt;
  
  
  Infinite Iterators
&lt;/h2&gt;

&lt;p&gt;Infinite iterators are a type of iterator that can produce an infinite sequence of values which results from an endless loop. To stop this, you have to specify a condition for breaking out of the loop.&lt;/p&gt;

&lt;p&gt;Itertools provides us with a few of these types of iterators which include&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;
Count(start, step)&lt;/li&gt;
&lt;/ul&gt;

&lt;p&gt;The count iterator will return evenly spaced numbers starting from the number passed into its start parameter. It also provides steps, which can be quite useful. Lets see how it works in practice&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;from itertools import count

for i in count(start=2, step=2):
    if i &amp;lt; 10:
        print(i)
    else:
        break

&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;In the code above, we first imported the count iterator from the itertools module. We then set up a for loop with the count iterator starting from 2 with a step size of 2. Later on, we set up a condition to break out of the loop if the iterator is greater than 10. The output of this code would be even numbers from 2 to 10, excluding 10 as shown below&lt;/p&gt;

&lt;p&gt;&lt;a href="https://res.cloudinary.com/practicaldev/image/fetch/s--uZxsmzSg--/c_limit%2Cf_auto%2Cfl_progressive%2Cq_auto%2Cw_800/https://lh4.googleusercontent.com/WqS1468_E4IECmM77cIyS_S8oqwHKXLEe0IExJzGBBOuaAWu83VFLFuSb2s66rCVTsAQ4kPbSIXNMAWhq1v_OBZj5C6-RPKXe_0OGY0e57N9EWN74K8CuOV3iGra_8elTHluSNYOFXx533aQpEH0Ync" class="article-body-image-wrapper"&gt;&lt;img src="https://res.cloudinary.com/practicaldev/image/fetch/s--uZxsmzSg--/c_limit%2Cf_auto%2Cfl_progressive%2Cq_auto%2Cw_800/https://lh4.googleusercontent.com/WqS1468_E4IECmM77cIyS_S8oqwHKXLEe0IExJzGBBOuaAWu83VFLFuSb2s66rCVTsAQ4kPbSIXNMAWhq1v_OBZj5C6-RPKXe_0OGY0e57N9EWN74K8CuOV3iGra_8elTHluSNYOFXx533aQpEH0Ync" alt="" width="800" height="272"&gt;&lt;/a&gt;&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;
Cycle(iterable)&lt;/li&gt;
&lt;/ul&gt;

&lt;p&gt;The cycle() iterator takes an iterable as an argument and iterates through each item of the iterable in perpetuity unless a condition is provided to break out of the loop as shown below:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;from itertools import cycle

tracker = 0
numbers = [1, 2]
for i in cycle(numbers):
    if tracker &amp;lt; 5:
        print(i)
    else:
        break
    tracker += 1

&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;In the code above, we import the cycle iterator, define a tracker variable to keep track of the number of iterations and set up an iterable in the form of a list containing two numbers. We then construct a for loop with the cycle iterator and pass in the list of numbers as an argument. Finally, we set up a condition to break out of the loop if the number of iterations(i.e. the tracker variable) is greater than five. The output of this code is shown below:&lt;/p&gt;

&lt;p&gt;&lt;a href="https://res.cloudinary.com/practicaldev/image/fetch/s--zfg__Ji1--/c_limit%2Cf_auto%2Cfl_progressive%2Cq_auto%2Cw_800/https://lh3.googleusercontent.com/BjhNiYcDQiKPvJ0AC9CfcqsgUha9Sk0xOrUtsmgAU-aGtbC-mUj5KlDpVj_w6eiqTKtfnkIgelCHof04lOZg9W25uHG_RdqGfjDjKewzCRlLHvjV7royIPT9CYFIU72BNuiR4XQqOImFBioqvVi51Yw" class="article-body-image-wrapper"&gt;&lt;img src="https://res.cloudinary.com/practicaldev/image/fetch/s--zfg__Ji1--/c_limit%2Cf_auto%2Cfl_progressive%2Cq_auto%2Cw_800/https://lh3.googleusercontent.com/BjhNiYcDQiKPvJ0AC9CfcqsgUha9Sk0xOrUtsmgAU-aGtbC-mUj5KlDpVj_w6eiqTKtfnkIgelCHof04lOZg9W25uHG_RdqGfjDjKewzCRlLHvjV7royIPT9CYFIU72BNuiR4XQqOImFBioqvVi51Yw" alt="" width="800" height="286"&gt;&lt;/a&gt;&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;
Repeat(object, times=None)&lt;/li&gt;
&lt;/ul&gt;

&lt;p&gt;The repeat iterator takes an object such as an iterable as an argument and returns the object infinitely unless its times parameter is provided with an argument as shown below&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;from itertools import repeat

numbers = [1, 2, 3, 4, 5]
for i in repeat(numbers, 5):
    print(i)

&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;In the code above, we imported the repeat iterator, then we defined an iterable in the form of a list of numbers. We then set up a for loop with the repeat iterator, passing in our list of numbers as an argument along with the number of times we want to repeat, in this case, 5. The output of the code is seen below:&lt;/p&gt;

&lt;p&gt;&lt;a href="https://res.cloudinary.com/practicaldev/image/fetch/s--bQ5xsODV--/c_limit%2Cf_auto%2Cfl_progressive%2Cq_auto%2Cw_800/https://lh6.googleusercontent.com/4ffTjnMdrZ7dimtMuhkhxYutfEBkpoQq877IMNEsUzs0f6j8_I6RZ3aLKoHmpGFmen-BRcqvX6nINabA25ut-wjYEUU2zGv5hnJdpkBZVJp4PCLtXi3gbE6QHSClCBsD62H64QT6Wj5EUkyzr4vueFA" class="article-body-image-wrapper"&gt;&lt;img src="https://res.cloudinary.com/practicaldev/image/fetch/s--bQ5xsODV--/c_limit%2Cf_auto%2Cfl_progressive%2Cq_auto%2Cw_800/https://lh6.googleusercontent.com/4ffTjnMdrZ7dimtMuhkhxYutfEBkpoQq877IMNEsUzs0f6j8_I6RZ3aLKoHmpGFmen-BRcqvX6nINabA25ut-wjYEUU2zGv5hnJdpkBZVJp4PCLtXi3gbE6QHSClCBsD62H64QT6Wj5EUkyzr4vueFA" alt="" width="800" height="286"&gt;&lt;/a&gt;&lt;/p&gt;

&lt;h2&gt;
  
  
  Finite Iterators
&lt;/h2&gt;

&lt;p&gt;Finite iterators are a type of iterator that have a finite or limited sequence of values to iterate over. They are usually associated with finite iterables. Itertools has quite a bunch of finite iterators for us to use.&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;
Accumulate(iterable)&lt;/li&gt;
&lt;/ul&gt;

&lt;p&gt;The accumulate iterator takes in an iterable as an argument and returns its accumulated sums. The default of the accumulate iterator is addition, but for this article, well be using the multiplication operator as shown below:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;from itertools import accumulate
from operator import mul

numbers = [1, 2, 3, 4, 5]
for i in accumulate(numbers, mul):
    print(i)

&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;In the code above, we imported the accumulate iterator and also imported the multiplication operator from the operator module. We then defined an iterable in the form of a list of numbers. Finally, we set up a for loop with the accumulate iterator, passing in our list of numbers along with the operator we wish to use, in this case, the multiplication operator from the operator module as arguments. This code should return the accumulated product of the numbers in our list as shown:&lt;/p&gt;

&lt;p&gt;&lt;a href="https://res.cloudinary.com/practicaldev/image/fetch/s--NUIR3NLe--/c_limit%2Cf_auto%2Cfl_progressive%2Cq_auto%2Cw_800/https://lh6.googleusercontent.com/k1m4cNTsjuXcjrNo5Ir1VShBcMkAxva3D1WuRAmhfxZumabtXmr8erxXEe3p9lQ3DcdnmFeYsG-OrSVBcMH1eskYU_En75LJG2YmjpeS_L4M08w6Eu5oXMMs_c9Xh2abFl9VwzzeFuygEVvstR_MI1M" class="article-body-image-wrapper"&gt;&lt;img src="https://res.cloudinary.com/practicaldev/image/fetch/s--NUIR3NLe--/c_limit%2Cf_auto%2Cfl_progressive%2Cq_auto%2Cw_800/https://lh6.googleusercontent.com/k1m4cNTsjuXcjrNo5Ir1VShBcMkAxva3D1WuRAmhfxZumabtXmr8erxXEe3p9lQ3DcdnmFeYsG-OrSVBcMH1eskYU_En75LJG2YmjpeS_L4M08w6Eu5oXMMs_c9Xh2abFl9VwzzeFuygEVvstR_MI1M" alt="" width="800" height="286"&gt;&lt;/a&gt;&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;
Compress(data, selectors)&lt;/li&gt;
&lt;/ul&gt;

&lt;p&gt;The compress iterator is quite handy for filtering the first iterable(data) with the second iterable(selectors). For this to work, we set the second iterable as a list of booleans which will be assigned to the selectors parameter. Lets show this in code:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;from itertools import compress
numbers = [1, 2, 3, 4, 5]
bool_list = [True, False, True, False, True]

for i in compress(numbers, bool_list):
    print(i)

&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;In the code above, we import the compress iterator, define a list of numbers which will be used as our data and define another list of booleans which will be used as our selectors.&lt;/p&gt;

&lt;p&gt;We then set up a for loop with the compress iterator, passing in our various lists as data and selectors. This code will return items in our first list (data) which match True in our second list (selectors) as shown below:&lt;/p&gt;

&lt;p&gt;&lt;a href="https://res.cloudinary.com/practicaldev/image/fetch/s--PPuA0j8D--/c_limit%2Cf_auto%2Cfl_progressive%2Cq_auto%2Cw_800/https://lh5.googleusercontent.com/KImkvvEUYzJfi_ndnakSVOhdDDAqTcjPiOOVO16lS-lDX3FjffiDnyh1OnTMzCey7WSDNFI51xi81s3iO3KjpC1iHlEoOxqC6DXVkTC8cWTETvth5cOLDoqlfLMAnOF-5jZmE4pr1sIoJ089c9QWDis" class="article-body-image-wrapper"&gt;&lt;img src="https://res.cloudinary.com/practicaldev/image/fetch/s--PPuA0j8D--/c_limit%2Cf_auto%2Cfl_progressive%2Cq_auto%2Cw_800/https://lh5.googleusercontent.com/KImkvvEUYzJfi_ndnakSVOhdDDAqTcjPiOOVO16lS-lDX3FjffiDnyh1OnTMzCey7WSDNFI51xi81s3iO3KjpC1iHlEoOxqC6DXVkTC8cWTETvth5cOLDoqlfLMAnOF-5jZmE4pr1sIoJ089c9QWDis" alt="" width="800" height="248"&gt;&lt;/a&gt;&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;
Dropwhile(predicate, iterable)&lt;/li&gt;
&lt;/ul&gt;

&lt;p&gt;The dropwhile iterator takes in a predicate which can be a function as an argument as well as an iterable. The dropwhile iterator will drop elements as long as the filter criteria is True but once it hits upon an element which when checked with the filter criteria is False, it keeps that element along with every other element that comes after. Fundamentally, this iterator &lt;strong&gt;drops&lt;/strong&gt; every item in the iterable &lt;strong&gt;while&lt;/strong&gt; it has not reached an item that evaluates to False. Lets show this with the code:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;
from itertools import dropwhile

def greater_than_three(x):
    return x &amp;gt; 3

num = [6, 4, 5, 6, 2, 6, 7, 9]
for i in dropwhile(greater_than_three, num):
    print(i)

&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;In the code above, we imported the dropwhile iterator, created a function that returns True if the number provided as argument is greater than three and finally defined an iterable in the form of a list of numbers. We then set up a for loop with the dropwhile iterator, passing in our predicate( the function) and iterable( list of numbers) as arguments. The output of this code will be every item in the list after the predicate hits upon an item in the list that returns False as shown:&lt;/p&gt;

&lt;p&gt;&lt;a href="https://res.cloudinary.com/practicaldev/image/fetch/s--sj8UAlbs--/c_limit%2Cf_auto%2Cfl_progressive%2Cq_auto%2Cw_800/https://lh3.googleusercontent.com/SGLfQpkQYli3Atl01Coz6YROkwue5gjr7IDK10-VbYQzzXIiR4BunpG1nP1Qh9h1FLWCM9lL7IpH0bmgsc2m6pAq7Cob5Aae9RuO8k96ikdaeGvFojJENA7Cl9SRvWd0YjJPzbKap3OxPg7GT-h8E1w" class="article-body-image-wrapper"&gt;&lt;img src="https://res.cloudinary.com/practicaldev/image/fetch/s--sj8UAlbs--/c_limit%2Cf_auto%2Cfl_progressive%2Cq_auto%2Cw_800/https://lh3.googleusercontent.com/SGLfQpkQYli3Atl01Coz6YROkwue5gjr7IDK10-VbYQzzXIiR4BunpG1nP1Qh9h1FLWCM9lL7IpH0bmgsc2m6pAq7Cob5Aae9RuO8k96ikdaeGvFojJENA7Cl9SRvWd0YjJPzbKap3OxPg7GT-h8E1w" alt="" width="800" height="267"&gt;&lt;/a&gt;&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;
Filterfalse(predicate, iterable)&lt;/li&gt;
&lt;/ul&gt;

&lt;p&gt;The filter false iterator takes in a predicate which can be a function as well as an iterable as arguments. It returns values of the iterable that evaluate to False when checked with the predicate and drops values that evaluate to True. Lets show this with the code:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;from itertools import filterfalse

def less_than_four(x):
    return x &amp;lt; 4

num = [6, 7, 8, 9 , 1, 6, 3, 0 , 9, 2]
for i in filterfalse(less_than_four, num):
    print(i)

&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;In the code above, we imported the filterfalse iterator, defined a function that returns True if the number passed into it is less than four and we also created an iterable in the form of a list of numbers. We then as usual, set up a for loop with the filterfalse iterator, passing in our function and iterable as arguments. This code will return items in our iterable that evaluate to False (i.e are greater than four) as shown:&lt;/p&gt;

&lt;p&gt;&lt;a href="https://res.cloudinary.com/practicaldev/image/fetch/s--7A2c__ik--/c_limit%2Cf_auto%2Cfl_progressive%2Cq_auto%2Cw_800/https://lh3.googleusercontent.com/YltfXwpshocOoNn3y2bU8A7xAIjh_WFkv0b8rxOVjChtRDDd8IGizmX4TS6S4nCoqY8sawMAoKl13sIbSx_KSmqWDWqJ_rDgMtLcWwtg6KNS63uY5YjJ0IMviYreJoZsv_xbvv8DN3XjahY3YaQgtWs" class="article-body-image-wrapper"&gt;&lt;img src="https://res.cloudinary.com/practicaldev/image/fetch/s--7A2c__ik--/c_limit%2Cf_auto%2Cfl_progressive%2Cq_auto%2Cw_800/https://lh3.googleusercontent.com/YltfXwpshocOoNn3y2bU8A7xAIjh_WFkv0b8rxOVjChtRDDd8IGizmX4TS6S4nCoqY8sawMAoKl13sIbSx_KSmqWDWqJ_rDgMtLcWwtg6KNS63uY5YjJ0IMviYreJoZsv_xbvv8DN3XjahY3YaQgtWs" alt="" width="800" height="324"&gt;&lt;/a&gt;&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;
Takewhile(predicate, iterable)&lt;/li&gt;
&lt;/ul&gt;

&lt;p&gt;The takewhile iterator takes a predicate and an iterable as arguments. It is the polar opposite of the dropwhile iterator. The takewhile iterator will return values of the iterable that evaluate to True from the predicate, but once it stumbles upon an item which evaluates to False it stops and drops the rest of the values in the iterable. Essentially, this iterator &lt;strong&gt;takes&lt;/strong&gt; every item in the iterable &lt;strong&gt;while&lt;/strong&gt; it has not reached an item that evaluates to False. Lets show this with the code:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;
from itertools import takewhile

def greater_than_three(x):
     return x &amp;gt; 3

num = [6, 4, 5, 6, 2, 6, 7, 9]
for i in takewhile(greater_than_three, num):
    print(i)

&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;In the code above, we imported the takewhile iterator, defined a function that returns True if the value passed to it is greater than three and we created our iterable as a list of numbers as usual. We then set up a for loop with the takewhile iterator, passing in our function and iterable as arguments. The output of this code will be every item in the list before the predicate hits upon an item in the list that returns False as shown:&lt;/p&gt;

&lt;p&gt;&lt;a href="https://res.cloudinary.com/practicaldev/image/fetch/s--bGBToruE--/c_limit%2Cf_auto%2Cfl_progressive%2Cq_auto%2Cw_800/https://lh5.googleusercontent.com/kmgwuWQhC5RU-unNpIAEi9EahQ57T_vJURXz96iGUOFoAkgOZhGx8h8J0lr7Jsx8cLLFnry7kFyv1VZmQBPDpAhORrXmyW7MIuvTka5XFvd_XwiHdMhgEtBZmK-cJbb80GBMk5-_Smj_-xCwY5wdh_U" class="article-body-image-wrapper"&gt;&lt;img src="https://res.cloudinary.com/practicaldev/image/fetch/s--bGBToruE--/c_limit%2Cf_auto%2Cfl_progressive%2Cq_auto%2Cw_800/https://lh5.googleusercontent.com/kmgwuWQhC5RU-unNpIAEi9EahQ57T_vJURXz96iGUOFoAkgOZhGx8h8J0lr7Jsx8cLLFnry7kFyv1VZmQBPDpAhORrXmyW7MIuvTka5XFvd_XwiHdMhgEtBZmK-cJbb80GBMk5-_Smj_-xCwY5wdh_U" alt="" width="800" height="267"&gt;&lt;/a&gt;&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;
Zip_longest(*iterables, fillvalue=None)&lt;/li&gt;
&lt;/ul&gt;

&lt;p&gt;The zip_longest iterator can be used to iterate over two iterables together. If the two iterables are not of the same length, you can provide a fill value to fill up the blank spots of the lesser or shorter iterable as shown below:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;from itertools import zip_longest

for i in zip_longest('abcd', '12', fillvalue='None'):
    print(i)

&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;In the code above, we import the zip_longest iterator and set up a for loop with it passing in two iterables and a fill value as arguments. The second iterable(12) is two characters short, so we provide a fill value of None to it. The output is shown below:&lt;/p&gt;

&lt;p&gt;&lt;a href="https://res.cloudinary.com/practicaldev/image/fetch/s--Z8dHNF5Z--/c_limit%2Cf_auto%2Cfl_progressive%2Cq_auto%2Cw_800/https://lh6.googleusercontent.com/mSj90woXveugNbjaqIOXH2W3ruGfZnu6fmUDu5cRIOErTK7gQ0aK5HP09i3-XFu9VAEhrsFMdUmy16LbVWDUGeGsG5KR43ZGNQomvE5QCPWimZ66bMUANArOjCwPdu2IIqSpHY8JbVQL0MlyuVMgcgo" class="article-body-image-wrapper"&gt;&lt;img src="https://res.cloudinary.com/practicaldev/image/fetch/s--Z8dHNF5Z--/c_limit%2Cf_auto%2Cfl_progressive%2Cq_auto%2Cw_800/https://lh6.googleusercontent.com/mSj90woXveugNbjaqIOXH2W3ruGfZnu6fmUDu5cRIOErTK7gQ0aK5HP09i3-XFu9VAEhrsFMdUmy16LbVWDUGeGsG5KR43ZGNQomvE5QCPWimZ66bMUANArOjCwPdu2IIqSpHY8JbVQL0MlyuVMgcgo" alt="" width="800" height="267"&gt;&lt;/a&gt;&lt;/p&gt;

&lt;h2&gt;
  
  
  Combinatoric Iterators
&lt;/h2&gt;

&lt;p&gt;Combinatoric iterators are a type of iterator that focuses on generating various combinations and permutations from an iterable. They are particularly useful for solving combinatorial problems. Itertools provides us with a handful of these combinatorial generators.&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;
Combinations(iterable, r)&lt;/li&gt;
&lt;/ul&gt;

&lt;p&gt;The combinations iterator takes an iterable as an argument along with an r-length tuple which is the length of each combination. Lets see this in the code:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;from itertools import combinations

for i in combinations('ABCD', 2):
    print(''.join(i))

&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;In the code above, we imported the combinations iterator and then set up a for loop with it, providing a String as an iterable and 2 as the length of each combination. This code would normally return a tuple of each combination, but after using the join method weve joined the two values that would have been in a tuple to a single String as shown below:&lt;/p&gt;

&lt;p&gt;&lt;a href="https://res.cloudinary.com/practicaldev/image/fetch/s--uHCPrfcm--/c_limit%2Cf_auto%2Cfl_progressive%2Cq_auto%2Cw_800/https://lh5.googleusercontent.com/EBC9fodUI47LE_IxUIczolgVD4DVtlqECCz9nsSwxIjLiGheTnuC5-SIu4bRY2YRZg0IGGra1MVsBTSEeUXhegO4ddi2LoMTSdPmwzrSXL0zRTn2S9FbFT8TCm1nbvCZ9aezV9vtuzPdtsObGAVSvP8" class="article-body-image-wrapper"&gt;&lt;img src="https://res.cloudinary.com/practicaldev/image/fetch/s--uHCPrfcm--/c_limit%2Cf_auto%2Cfl_progressive%2Cq_auto%2Cw_800/https://lh5.googleusercontent.com/EBC9fodUI47LE_IxUIczolgVD4DVtlqECCz9nsSwxIjLiGheTnuC5-SIu4bRY2YRZg0IGGra1MVsBTSEeUXhegO4ddi2LoMTSdPmwzrSXL0zRTn2S9FbFT8TCm1nbvCZ9aezV9vtuzPdtsObGAVSvP8" alt="" width="800" height="306"&gt;&lt;/a&gt;&lt;/p&gt;

&lt;p&gt;It is important to note that the combination is done in a lexicographic manner (i.e. alphabetically, A-Z). Also, the combinations will not produce repeat values(e.g. AA, BB) if all the input elements are unique.&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;
Combinations_with_replacement(iterable, r)&lt;/li&gt;
&lt;/ul&gt;

&lt;p&gt;The combinations_with_replacement iterator is quite similar to the combinations iterator, except in this case, it creates combinations where elements do repeat (e.g. AA, BB). Lets see this in the code:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;from itertools import combinations_with_replacement

for i in combinations_with_replacement('ABCD', 2):
    print(''.join(i))

&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;&lt;a href="https://res.cloudinary.com/practicaldev/image/fetch/s--d9oOKwwo--/c_limit%2Cf_auto%2Cfl_progressive%2Cq_auto%2Cw_800/https://cdn.hashnode.com/res/hashnode/image/upload/v1690302207421/77332dee-18f5-4c0e-8a3c-e8910295479f.png" class="article-body-image-wrapper"&gt;&lt;img src="https://res.cloudinary.com/practicaldev/image/fetch/s--d9oOKwwo--/c_limit%2Cf_auto%2Cfl_progressive%2Cq_auto%2Cw_800/https://cdn.hashnode.com/res/hashnode/image/upload/v1690302207421/77332dee-18f5-4c0e-8a3c-e8910295479f.png" alt="" width="800" height="382"&gt;&lt;/a&gt;&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;
Permutations(iterable, r)&lt;/li&gt;
&lt;/ul&gt;

&lt;p&gt;The permutations iterator returns a progression of r-length permutations of elements of the iterable you give to it. Lets see this in code:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;from itertools import permutations

for i in permutations('ABCD', 2):
    print(''.join(i))

&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;&lt;a href="https://res.cloudinary.com/practicaldev/image/fetch/s--b9UvwcbM--/c_limit%2Cf_auto%2Cfl_progressive%2Cq_auto%2Cw_800/https://lh5.googleusercontent.com/xKTRAxUuHK0Okz_hzXFipakRkmmCTUr8VC7HWlzadOztOG94N1ojBhoT33VgsokFSDHwmn-5lV-DrCL4YK-J0Lg7QaQj9Z0vGrM1Y9SZLm49p1ZQgHTithkbrcPHOd4j5CrdrgPN98bB3GGkbkfoObk" class="article-body-image-wrapper"&gt;&lt;img src="https://res.cloudinary.com/practicaldev/image/fetch/s--b9UvwcbM--/c_limit%2Cf_auto%2Cfl_progressive%2Cq_auto%2Cw_800/https://lh5.googleusercontent.com/xKTRAxUuHK0Okz_hzXFipakRkmmCTUr8VC7HWlzadOztOG94N1ojBhoT33VgsokFSDHwmn-5lV-DrCL4YK-J0Lg7QaQj9Z0vGrM1Y9SZLm49p1ZQgHTithkbrcPHOd4j5CrdrgPN98bB3GGkbkfoObk" alt="" width="800" height="419"&gt;&lt;/a&gt;&lt;/p&gt;

&lt;p&gt;Thats it for this article, as you can see, the itertools module provides us with a collection of very handy functions that we can use for efficient iteration without coding them from scratch by ourselves. For a more comprehensive outlook on more of these tools be sure to visit the &lt;a href="https://docs.python.org/3/library/itertools.html"&gt;docs&lt;/a&gt;.&lt;/p&gt;

</description>
    </item>
    <item>
      <title>Building A Mail Client With  Python</title>
      <dc:creator>Favour George</dc:creator>
      <pubDate>Tue, 18 Jul 2023 19:03:38 +0000</pubDate>
      <link>https://dev.to/psycode99/building-a-mail-client-with-python-i26</link>
      <guid>https://dev.to/psycode99/building-a-mail-client-with-python-i26</guid>
      <description>&lt;h1&gt;
  
  
  What is a Mail Client?
&lt;/h1&gt;

&lt;p&gt;A mail client is a program used to manage and compose emails that can be sent as well as received. A mail client is only ever active when it is being run by a user.&lt;/p&gt;

&lt;p&gt;In this project, well be creating a rudimentary version of a mail client to send emails with attachments such as images in the Python programming language.&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;PROJECT REQUIREMENTS:&lt;/strong&gt; To build this project, youll need a Gmail account. In addition, in your project folder youll need:&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;&lt;p&gt;A message text file containing the email's message&lt;/p&gt;&lt;/li&gt;
&lt;li&gt;&lt;p&gt;An image file of your choice&lt;/p&gt;&lt;/li&gt;
&lt;/ul&gt;

&lt;p&gt;Lets get started building our highly ineffective but usable mail client:&lt;/p&gt;

&lt;h1&gt;
  
  
  &lt;strong&gt;Defining Import Statements&lt;/strong&gt;
&lt;/h1&gt;

&lt;p&gt;In this section, well be importing the necessary libraries we need to build this project into our &lt;a href="http://main.py"&gt;main.py&lt;/a&gt; file in our project directory&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;import smtplib
from email.mime.text import MIMEText
from email.mime.base import MIMEBase
from email.mime.multipart import MIMEMultipart
from email import encoders

&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;Lets understand what each import statement above does:&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;&lt;p&gt;&lt;strong&gt;smtplib:&lt;/strong&gt; This is the Python library well be using to send emails&lt;/p&gt;&lt;/li&gt;
&lt;li&gt;&lt;p&gt;&lt;strong&gt;MIMEText:&lt;/strong&gt; This class will be used to wrap our emails message to provide better formatting.&lt;/p&gt;&lt;/li&gt;
&lt;li&gt;&lt;p&gt;&lt;strong&gt;MIMEBase:&lt;/strong&gt; The MIMEBase class adds a content-type header to the email.&lt;/p&gt;&lt;/li&gt;
&lt;li&gt;&lt;p&gt;&lt;strong&gt;MIMEMultipart:&lt;/strong&gt; This class is used to create an object that will contain information that will be in the emails header such as the from address, to address and email subject.&lt;/p&gt;&lt;/li&gt;
&lt;li&gt;&lt;p&gt;&lt;strong&gt;encoders:&lt;/strong&gt; This will be used to encode our payload, in our case, the image, to a base64 format.&lt;/p&gt;&lt;/li&gt;
&lt;/ul&gt;

&lt;h1&gt;
  
  
  &lt;strong&gt;Setting Up Our Credentials&lt;/strong&gt;
&lt;/h1&gt;

&lt;p&gt;In this section, well set up the login details for our Gmail account; email address and app password as shown below:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;credentials = __import__ ("credentials")
email_address = credentials.email
password = credentials.app_password
to_addr = credentials.to_address

&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;In the code above, I had already created a file named &lt;a href="http://credentials.py"&gt;credentials.py&lt;/a&gt;, and in it, I stored my email address and app password as well as the email address I'm sending the email. So all I did was import them into my &lt;a href="http://main.py"&gt;main.py&lt;/a&gt; file and assign them to variables as shown above. If the code you are writing won't be shared anywhere, feel free to include the email address and password directly into the code.&lt;/p&gt;

&lt;p&gt;Now, you may have heard me say the app password above twice and thats because its important to understand that this is different from your Gmail accounts password. Now, the app password is a safer way to access your Gmail account outside Gmail itself through our code. To set up an app password follow the steps below:&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;&lt;p&gt;Login to your Google account&lt;/p&gt;&lt;/li&gt;
&lt;li&gt;&lt;p&gt;Go to the security tab&lt;/p&gt;&lt;/li&gt;
&lt;li&gt;&lt;p&gt;Enable 2-factor authentication&lt;/p&gt;&lt;/li&gt;
&lt;li&gt;&lt;p&gt;After enabling 2-factor authentication, in the 2-factor authentication section scroll down, and youll find a section on creating an app password. Create one.&lt;/p&gt;&lt;/li&gt;
&lt;li&gt;&lt;p&gt;Copy the password which will be 16 characters long and paste it where you are assigning the password in your code&lt;/p&gt;&lt;/li&gt;
&lt;/ul&gt;

&lt;p&gt;This &lt;a href="https://www.youtube.com/watch?v=Y_u5KIeXiVI"&gt;YouTube video&lt;/a&gt; provides a clearer explanation of how to set up an app password.&lt;/p&gt;

&lt;h1&gt;
  
  
  &lt;strong&gt;Setting up the Email Header&lt;/strong&gt;
&lt;/h1&gt;

&lt;p&gt;In this section well be setting the contents of our email header which will include things such as the from address, to address and email subject&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;msg = MIMEMultipart()
msg['From'] = "Mad Max"
msg["To"] = to_addr
msg["Subject"] = "Hello nerd, its Mad Max"

&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;In the code above, we created an instance of the MIMEMultipart class. Think of the object instantiated as a dictionary, to which we can assign values to its keys. In this case, we've assigned the "from email address", "to email address" and "subject" to their respective keys.&lt;/p&gt;

&lt;h1&gt;
  
  
  &lt;strong&gt;Reading our Message File&lt;/strong&gt;
&lt;/h1&gt;

&lt;p&gt;Now we'll read the message text file we created and stored in our project folder&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;with open("message.txt", 'r') as message:
    subject = message.read()
    msg.attach(MIMEText(subject, "plain"))

&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;In the code above, we opened our message.txt file in read mode, 'r'. We then read the file and attached it to the message as a plain text document through the MIMEText class.&lt;/p&gt;

&lt;h1&gt;
  
  
  &lt;strong&gt;Attaching a File&lt;/strong&gt;
&lt;/h1&gt;

&lt;p&gt;We'll now be attaching a file to our message body&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;attached_file = "mad_max.png"
with open(attached_file, "rb") as attachment:
    payload = MIMEBase("application", "octet-stream")
    payload.set_payload(attachment.read())

    encoders.encode_base64(payload)
    payload.add_header("Content-Disposition", f"attachment; filename={attached_file}")
    msg.attach(payload)

&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;First of all, we read our file in read binary mode, 'rb' because we are dealing with an image file and not an ordinary text file. Next, we instantiate the MIMEBase class and set a payload of our read image file. We then encode the payload to base64 as good practice and then add a header and finally attach the payload to the email message body.&lt;/p&gt;

&lt;h1&gt;
  
  
  &lt;strong&gt;Sending our Email&lt;/strong&gt;
&lt;/h1&gt;

&lt;p&gt;To send our email, we'll be using the SMTP library of Python as shown below&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;text = msg.as_string()
with smtplib.SMTP("smtp.gmail.com", 587) as server:
    server.starttls()
    server.login(email_address, password)
    server.sendmail(email_address, to_addr, text)

&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;Before sending our email, we convert the entire message body to string just for good measure. Then we create a connection with the SMTP service of our email service provider, in this case, Gmail, on their specified port, 587. The starttls() method enables us to establish a secure connection to our email service provider. We then log in using the credentials we provided above(email address and password) and finally send the mail specifying the email address we are sending from, the address we are sending to and the contents of the email.&lt;/p&gt;

&lt;p&gt;If everything was successful and the code ran without errors, the email should be in the inbox of the email address it was sent to as shown below&lt;/p&gt;

&lt;p&gt;&lt;a href="https://res.cloudinary.com/practicaldev/image/fetch/s--DKmjfHWM--/c_limit%2Cf_auto%2Cfl_progressive%2Cq_auto%2Cw_800/https://lh4.googleusercontent.com/Aa2qX5MbqJD3_REPEX0cHZ5ni-WFl5I949PvVqKix15LhClitYI0oy2Deb3CJWjrWOhRdZlFcuYMEmQVK9y9bAWksR0vbIWR1Bs_vkcFdagTSF_ZOAp_od0wpw1VHK-FHOAPODcmyY6-LYLahD36CnY" class="article-body-image-wrapper"&gt;&lt;img src="https://res.cloudinary.com/practicaldev/image/fetch/s--DKmjfHWM--/c_limit%2Cf_auto%2Cfl_progressive%2Cq_auto%2Cw_800/https://lh4.googleusercontent.com/Aa2qX5MbqJD3_REPEX0cHZ5ni-WFl5I949PvVqKix15LhClitYI0oy2Deb3CJWjrWOhRdZlFcuYMEmQVK9y9bAWksR0vbIWR1Bs_vkcFdagTSF_ZOAp_od0wpw1VHK-FHOAPODcmyY6-LYLahD36CnY" alt="" width="637" height="1080"&gt;&lt;/a&gt;&lt;/p&gt;

&lt;p&gt;From the image above, you can confirm that I've successfully received the email sent from our crappy mail client and that our code ran without any errors, thus far.&lt;/p&gt;

&lt;p&gt;Here's the complete code and a link to the project on &lt;a href="https://github.com/psycode99/mailing_client/tree/master"&gt;GitHub&lt;/a&gt;.&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;import smtplib
from email.mime.text import MIMEText
from email.mime.base import MIMEBase
from email.mime.multipart import MIMEMultipart
from email import encoders

credentials = __import__ ("credentials")
email_address = credentials.email
password = credentials.app_password
to_addr = credentials.to_address

msg = MIMEMultipart()
msg['From'] = "Mad Max"
msg["To"] = to_addr
msg["Subject"] = "Hello nerd, its Mad Max"

with open("message.txt", 'r') as message:
    subject = message.read()
    msg.attach(MIMEText(subject, "plain"))

attached_file = "mad_max.png"
with open(attached_file, "rb") as attachment:
    payload = MIMEBase("application", "octet-stream")
    payload.set_payload(attachment.read())

    encoders.encode_base64(payload)
    payload.add_header("Content-Disposition", f"attachment; filename={attached_file}")
    msg.attach(payload)

text = msg.as_string()
with smtplib.SMTP("smtp.gmail.com", 587) as server:
    server.starttls()
    server.login(email_address, password)
    server.sendmail(email_address, to_addr, text)

&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;That's it for this article, thanks for reading and hopefully building along. Let me know in the comments about any issues you might have gotten into while building.&lt;/p&gt;

</description>
    </item>
    <item>
      <title>A Step by Step Guide to Code Profiling in Python</title>
      <dc:creator>Favour George</dc:creator>
      <pubDate>Sun, 16 Jul 2023 13:13:28 +0000</pubDate>
      <link>https://dev.to/psycode99/a-step-by-step-guide-to-code-profiling-in-python-31dj</link>
      <guid>https://dev.to/psycode99/a-step-by-step-guide-to-code-profiling-in-python-31dj</guid>
      <description>&lt;p&gt;As programmers and software developers writing code is not enough, just because the code works doesnt mean it is effective. Optimizing our code for improved performance should be one of the tenets of software development. Code profiling helps us to achieve this by helping developers to find bottlenecks and redundancies in their software and fix them.&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;Prerequisites&lt;/strong&gt; : Knowledge of the Python programming language is crucial&lt;/p&gt;

&lt;h1&gt;
  
  
  Definition of Code Profiling
&lt;/h1&gt;

&lt;ul&gt;
&lt;li&gt;
What is Code Profiling:&lt;/li&gt;
&lt;/ul&gt;

&lt;p&gt;In software engineering, profiling ("program profiling", "software profiling") is a form of dynamic program analysis that measures, for example, the space (memory) or time complexity of a program, the usage of particular instructions, or the frequency and duration of function calls. Most commonly, profiling information serves to aid program optimization, and more specifically, performance engineering. - &lt;a href="https://en.m.wikipedia.org/wiki/Profiling_(computer_programming)"&gt;Wikipedia&lt;/a&gt;&lt;/p&gt;

&lt;p&gt;Code profiling refers to the proper appraisal and examination of a software's source code to find the slowest parts of the code as well as parts that are consuming a lot of resources and optimize these parts of the code to improve the performance of the software.&lt;/p&gt;

&lt;h1&gt;
  
  
  The Purpose of Code Profiling
&lt;/h1&gt;

&lt;ul&gt;
&lt;li&gt;
Why is Code Profiling Necessary&lt;/li&gt;
&lt;/ul&gt;

&lt;p&gt;Code profiling is necessary to help software developers and engineers find bottlenecks in the source code of their software. These bottlenecks could result in performance issues such as poor user experience and overconsumption of resources. Code Profiling helps developers find parts of their code containing such bottlenecks and fix them.&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;
What is Code Optimization&lt;/li&gt;
&lt;/ul&gt;

&lt;p&gt;Code optimization is a set of procedures taken to improve code by making it consume lesser resources while also providing high performance.&lt;/p&gt;

&lt;p&gt;Code profiling can be said to be a form of code optimization as it aids software developers reach their software performance goals by providing an interface to help them find bottlenecks preventing them from achieving these goals in their code.&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;
Profiling Tools&lt;/li&gt;
&lt;/ul&gt;

&lt;p&gt;These are software or libraries that aid software developers in the code profiling process. For this article, we'll be looking at a few code profiling libraries from the Python programming language.&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;
&lt;strong&gt;timeit&lt;/strong&gt;
&lt;/li&gt;
&lt;/ul&gt;

&lt;p&gt;This Python module allows developers to be able to time small bits of their Python code. &lt;a href="https://docs.python.org/3/library/timeit.html"&gt;timeit docs&lt;/a&gt;.&lt;/p&gt;

&lt;p&gt;Let's try to time a simple Python code with timeit&lt;/p&gt;

&lt;p&gt;&lt;a href="https://res.cloudinary.com/practicaldev/image/fetch/s--4Q5UccrP--/c_limit%2Cf_auto%2Cfl_progressive%2Cq_auto%2Cw_800/https://lh6.googleusercontent.com/5PqvjF2TVJFfMDSe5iTWkcGTpQycCBqaccKRatZjiotBzAGMAp-EUX6UjY67QBxHXzk1MUeU093TMct_FeZzdF1i365iUtUqdYRFTmBUeN0fM1aomKyAcYFmUVGf55yHmF11q2_Jb3ujemQnu5INjYo" class="article-body-image-wrapper"&gt;&lt;img src="https://res.cloudinary.com/practicaldev/image/fetch/s--4Q5UccrP--/c_limit%2Cf_auto%2Cfl_progressive%2Cq_auto%2Cw_800/https://lh6.googleusercontent.com/5PqvjF2TVJFfMDSe5iTWkcGTpQycCBqaccKRatZjiotBzAGMAp-EUX6UjY67QBxHXzk1MUeU093TMct_FeZzdF1i365iUtUqdYRFTmBUeN0fM1aomKyAcYFmUVGf55yHmF11q2_Jb3ujemQnu5INjYo" alt="" width="762" height="632"&gt;&lt;/a&gt;&lt;/p&gt;

&lt;p&gt;In the code above we first import the timeit module.&lt;/p&gt;

&lt;p&gt;We then use the timeit.timeit() method to time a piece of code which is declared as a statement in the method's " &lt;strong&gt;&lt;em&gt;stmt&lt;/em&gt;&lt;/strong&gt;" keyword argument. The "number" keyword argument refers to the number of times the statement provided is going to be executed by the method. In the end, this method returns a floating point number of the time it took for the statement provided to be executed in seconds which we stored in the variable, "value" and printed out as shown below:&lt;/p&gt;

&lt;p&gt;&lt;a href="https://res.cloudinary.com/practicaldev/image/fetch/s--xpbHbNIg--/c_limit%2Cf_auto%2Cfl_progressive%2Cq_auto%2Cw_800/https://lh4.googleusercontent.com/aehqbW7jzKa8l0qqhJ0R9omB6lwvzPcTGCyRGEL8fPoVUoTnzTUP7RtP02PLqM8rOzlhfFTk9_apj6PmdLYj5FgNX-NmoZTPdkeeKWRmjfH_c-x5n7Ff1tgK7zzPUKIGm5WONuoDFXLpqnFhwJOeLMw" class="article-body-image-wrapper"&gt;&lt;img src="https://res.cloudinary.com/practicaldev/image/fetch/s--xpbHbNIg--/c_limit%2Cf_auto%2Cfl_progressive%2Cq_auto%2Cw_800/https://lh4.googleusercontent.com/aehqbW7jzKa8l0qqhJ0R9omB6lwvzPcTGCyRGEL8fPoVUoTnzTUP7RtP02PLqM8rOzlhfFTk9_apj6PmdLYj5FgNX-NmoZTPdkeeKWRmjfH_c-x5n7Ff1tgK7zzPUKIGm5WONuoDFXLpqnFhwJOeLMw" alt="" width="654" height="446"&gt;&lt;/a&gt;&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;
cProfile&lt;/li&gt;
&lt;/ul&gt;

&lt;p&gt;This Python module is used to measure the time it takes for a function to be executed as well as the number of times a function is executed. &lt;a href="https://docs.python.org/3/library/profile.html#module-cProfile"&gt;cProfile docs&lt;/a&gt;.&lt;/p&gt;

&lt;p&gt;Now let's try using cProfile to time a simple function&lt;/p&gt;

&lt;p&gt;&lt;a href="https://res.cloudinary.com/practicaldev/image/fetch/s--pVZtou-N--/c_limit%2Cf_auto%2Cfl_progressive%2Cq_auto%2Cw_800/https://lh3.googleusercontent.com/0NQ44Wcv2KUGGxb4yHdjOQMCltnf67KK3zixPvsKvFYPW2tiM0zWwGkezeF3Hzv82Ou5lbfWn68k07mGw_4kXUf10bOmH5gJ0oRtNbJvqOL4elSUpM2NMNWRD-wFLCTXyOLx_v6xD1zzh_Qdw38vMXg" class="article-body-image-wrapper"&gt;&lt;img src="https://res.cloudinary.com/practicaldev/image/fetch/s--pVZtou-N--/c_limit%2Cf_auto%2Cfl_progressive%2Cq_auto%2Cw_800/https://lh3.googleusercontent.com/0NQ44Wcv2KUGGxb4yHdjOQMCltnf67KK3zixPvsKvFYPW2tiM0zWwGkezeF3Hzv82Ou5lbfWn68k07mGw_4kXUf10bOmH5gJ0oRtNbJvqOL4elSUpM2NMNWRD-wFLCTXyOLx_v6xD1zzh_Qdw38vMXg" alt="" width="762" height="670"&gt;&lt;/a&gt;&lt;/p&gt;

&lt;p&gt;In the code above, we first import cProfile as profile. We then create a function named loop which takes an argument "text" and prints it out when being called. Lastly, we called the run() method of the cProfile module and provided the function call as an argument. After the code ran, it provided the statistics shown below&lt;/p&gt;

&lt;p&gt;&lt;a href="https://res.cloudinary.com/practicaldev/image/fetch/s--o4ooE32I--/c_limit%2Cf_auto%2Cfl_progressive%2Cq_auto%2Cw_800/https://lh3.googleusercontent.com/BpW-nloa4biBZUSdPK9ziffKT2okS5oV4ad8yCGCM8mCQU_jSHT0Rsn39c_2L4MWsJ2LtESkJuGbV9frdgGyi4RBctTpqjc6vFmSM-z2ufUwcYEDBGbE5pqLelezduS-_Pq0IpkvXZBPYnZTUv1UWgY" class="article-body-image-wrapper"&gt;&lt;img src="https://res.cloudinary.com/practicaldev/image/fetch/s--o4ooE32I--/c_limit%2Cf_auto%2Cfl_progressive%2Cq_auto%2Cw_800/https://lh3.googleusercontent.com/BpW-nloa4biBZUSdPK9ziffKT2okS5oV4ad8yCGCM8mCQU_jSHT0Rsn39c_2L4MWsJ2LtESkJuGbV9frdgGyi4RBctTpqjc6vFmSM-z2ufUwcYEDBGbE5pqLelezduS-_Pq0IpkvXZBPYnZTUv1UWgY" alt="" width="800" height="428"&gt;&lt;/a&gt;&lt;/p&gt;

&lt;h1&gt;
  
  
  Interpreting Profiling Results
&lt;/h1&gt;

&lt;p&gt;Profiling code is just one piece of the puzzle, understanding the output or metrics used by profilers to profile the code is another part of the puzzle.&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;
Understanding the Metrics&lt;/li&gt;
&lt;/ul&gt;

&lt;p&gt;When using the timeit module to time a piece of code the output was relatively easy to comprehend but for more complex outputs such as the one given by cProfile, understanding the multiple metrics used to profile the code becomes essential.&lt;/p&gt;

&lt;p&gt;For this example, we'll be interpreting the results of the cProfile profiler we saw above.&lt;/p&gt;

&lt;p&gt;&lt;a href="https://res.cloudinary.com/practicaldev/image/fetch/s--GHgH8N2Z--/c_limit%2Cf_auto%2Cfl_progressive%2Cq_auto%2Cw_800/https://lh3.googleusercontent.com/8uIbWd9mf4MXUfE2PVgOMb4a33T0iJflx1iKVWNdsvF3pWkY67LzC58zx_y1UV68kY0yDBVZmzOnk8-kyy64l2ECHG-0kjq4pnOVuKD2ju2X-OZM57sy49YZTO-decMH4syskmbXPbS2X6VP3SB0Xio" class="article-body-image-wrapper"&gt;&lt;img src="https://res.cloudinary.com/practicaldev/image/fetch/s--GHgH8N2Z--/c_limit%2Cf_auto%2Cfl_progressive%2Cq_auto%2Cw_800/https://lh3.googleusercontent.com/8uIbWd9mf4MXUfE2PVgOMb4a33T0iJflx1iKVWNdsvF3pWkY67LzC58zx_y1UV68kY0yDBVZmzOnk8-kyy64l2ECHG-0kjq4pnOVuKD2ju2X-OZM57sy49YZTO-decMH4syskmbXPbS2X6VP3SB0Xio" alt="" width="800" height="428"&gt;&lt;/a&gt;&lt;/p&gt;

&lt;p&gt;The cProfile output is divided into five distinct parts:&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;&lt;p&gt;&lt;strong&gt;ncalls&lt;/strong&gt; : This is the number of times the function is called.&lt;/p&gt;&lt;/li&gt;
&lt;li&gt;&lt;p&gt;&lt;strong&gt;tottime&lt;/strong&gt; : This refers to the total time spent in the function without taking into consideration other function calls.&lt;/p&gt;&lt;/li&gt;
&lt;li&gt;&lt;p&gt;&lt;strong&gt;percall&lt;/strong&gt; : This refers to the time spent for a single call of the function.&lt;/p&gt;&lt;/li&gt;
&lt;li&gt;&lt;p&gt;&lt;strong&gt;cumtime&lt;/strong&gt; : This refers to the time spent in the function including other function calls.&lt;/p&gt;&lt;/li&gt;
&lt;li&gt;&lt;p&gt;&lt;strong&gt;filename:lineno&lt;/strong&gt; : This refers to the filename and its corresponding line numbers.&lt;/p&gt;&lt;/li&gt;
&lt;/ul&gt;

&lt;h1&gt;
  
  
  Profiling Best Practices
&lt;/h1&gt;

&lt;p&gt;These are a few procedures to take to make the code profiling process smoother&lt;/p&gt;

&lt;ol&gt;
&lt;li&gt;&lt;p&gt;&lt;strong&gt;Write Concise Code:&lt;/strong&gt; it is important to make sure your code is clear and concise. Chunk your code into smaller pieces. Also, make sure that each function handles only one operation. &lt;/p&gt;&lt;/li&gt;
&lt;li&gt;&lt;p&gt;&lt;strong&gt;Be Patient:&lt;/strong&gt; profiling code can be a long and tedious process as some of the bottlenecks don't come off easily. Equally, profiling a long codebase will also require patience.&lt;/p&gt;&lt;/li&gt;
&lt;/ol&gt;

&lt;h1&gt;
  
  
  Profiling Case Study
&lt;/h1&gt;

&lt;p&gt;This will show a simple practical use case of code profiling.&lt;/p&gt;

&lt;p&gt;Case Study&lt;/p&gt;

&lt;p&gt;&lt;a href="https://res.cloudinary.com/practicaldev/image/fetch/s--xRFBp6F9--/c_limit%2Cf_auto%2Cfl_progressive%2Cq_auto%2Cw_800/https://lh6.googleusercontent.com/eoawE0pPbCk8idt29F2c39g96eY4Wynn4_gVFmGX-SEPNfgLiy3IKmye4i665MLl209bDIyIDlWWaezmA-ZK2gOwEylPqMtZLLcjREkZvuT_g6v0sRraxM-FkttlQTDZUhHlqdMIScroUiNFo6Ecol8" class="article-body-image-wrapper"&gt;&lt;img src="https://res.cloudinary.com/practicaldev/image/fetch/s--xRFBp6F9--/c_limit%2Cf_auto%2Cfl_progressive%2Cq_auto%2Cw_800/https://lh6.googleusercontent.com/eoawE0pPbCk8idt29F2c39g96eY4Wynn4_gVFmGX-SEPNfgLiy3IKmye4i665MLl209bDIyIDlWWaezmA-ZK2gOwEylPqMtZLLcjREkZvuT_g6v0sRraxM-FkttlQTDZUhHlqdMIScroUiNFo6Ecol8" alt="" width="762" height="1004"&gt;&lt;/a&gt;&lt;/p&gt;

&lt;p&gt;In the code above, we created two functions, one of the functions has a little time delay of three seconds while the other has no time delay.&lt;/p&gt;

&lt;p&gt;Assuming this time delay is a bottleneck, let's see if the cProfile profiler will detect this slight delay once we run the code&lt;/p&gt;

&lt;h2&gt;
  
  
  Output
&lt;/h2&gt;

&lt;p&gt;&lt;a href="https://res.cloudinary.com/practicaldev/image/fetch/s--5VX6TVFO--/c_limit%2Cf_auto%2Cfl_progressive%2Cq_auto%2Cw_800/https://lh4.googleusercontent.com/h_4gJz6KUm3cA_-LHsDA_Qw6fok3u0K8rYNZTHGnDYFLi2FwcUrqZGBL4ytcENLt2Yg939YcNXHVYaLtRPS68x_fCPX39SOaRK_KCESv3FXRUw6an80TDYj-d15N8QtN_-tqMzUbnDsKpl0KhLUom78" class="article-body-image-wrapper"&gt;&lt;img src="https://res.cloudinary.com/practicaldev/image/fetch/s--5VX6TVFO--/c_limit%2Cf_auto%2Cfl_progressive%2Cq_auto%2Cw_800/https://lh4.googleusercontent.com/h_4gJz6KUm3cA_-LHsDA_Qw6fok3u0K8rYNZTHGnDYFLi2FwcUrqZGBL4ytcENLt2Yg939YcNXHVYaLtRPS68x_fCPX39SOaRK_KCESv3FXRUw6an80TDYj-d15N8QtN_-tqMzUbnDsKpl0KhLUom78" alt="" width="800" height="782"&gt;&lt;/a&gt;&lt;/p&gt;

&lt;p&gt;From the output above, we can say that cProfile successfully detected the delay in the first function as seen in the time it took to execute the function.&lt;/p&gt;

&lt;p&gt;In conclusion, code profiling is a great way of optimizing our code for improved performance by finding the bottlenecks preventing it from running at its peak performance.&lt;/p&gt;

</description>
    </item>
    <item>
      <title>Charting Your Path to Web Development Mastery: A Roadmap for Success</title>
      <dc:creator>Favour George</dc:creator>
      <pubDate>Sun, 16 Jul 2023 12:45:39 +0000</pubDate>
      <link>https://dev.to/psycode99/charting-your-path-to-web-development-mastery-a-roadmap-for-success-59b0</link>
      <guid>https://dev.to/psycode99/charting-your-path-to-web-development-mastery-a-roadmap-for-success-59b0</guid>
      <description>&lt;p&gt;So you've finally decided to take that bold step of learning to code, perhaps for fun or to get a new job and settle into the IT industry. You decide to take on Web Development and search on Google how to go about it, but you get carried away by the vast amount of information and opinions you get.&lt;/p&gt;

&lt;p&gt;Should you become a Front-end developer? Back-end developer? Full-stack or Senior Developer? Should you learn React or Angular? Is No-SQL better than SQL databases? What is the MERN stack?&lt;/p&gt;

&lt;p&gt;Technically there's an information overload out there and it's easy to get lost in all of it. I won't say this article is any different from the others you've read on getting started in Web Development, 'cos it's not, I just intend to make it more definitive.&lt;/p&gt;

&lt;h1&gt;
  
  
  STEP 1: KNOW THE BASICS
&lt;/h1&gt;

&lt;p&gt;Yeah, before you get on to building the Instagram clone or any fantasy project of yours, you've got to appease the basics which are:&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;
HTML - HyperText Markup Language&lt;/li&gt;
&lt;/ul&gt;

&lt;p&gt;HTML allows you to lay the basic foundation for your website or web app. Though it's an ugly thing both when typing it and when it's visualized on a browser, it's a necessary evil. While learning HTML you need to get familiar with the Semantic Tags. It's also important to know that HTML is not a programming language but just a markup language&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;
CSS - Cascading Style Sheets&lt;/li&gt;
&lt;/ul&gt;

&lt;p&gt;Now CSS allows you to style your ugly-looking HTML code into something visually appealing and somewhat lovable. While learning CSS you will need to get acquainted with basic CSS syntax, Positioning, Selectors, Layout(Flex &amp;amp; Grid), Transitions and Animations as well as Responsive Design.&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;
JavaScript&lt;/li&gt;
&lt;/ul&gt;

&lt;p&gt;JavaScript is a real programming language and I mean as real as it gets. You can use JavaScript to create websites, games, mobile apps etc. But for this article, you can use JavaScript to add functionality to your website like clicking a button to give the site a dark theme. Equally, while learning JavaScript you need to get quite comfy with basic JavaScript syntax, data types, DOM &amp;amp; styling, JSON, HTTP Requests etc.&lt;/p&gt;

&lt;p&gt;Other technologies worth learning at this stage include:&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;&lt;p&gt;Version Control System (e.g Git)&lt;/p&gt;&lt;/li&gt;
&lt;li&gt;&lt;p&gt;Browser Developer Tools&lt;/p&gt;&lt;/li&gt;
&lt;li&gt;&lt;p&gt;Deployment (e.g Netlify)&lt;/p&gt;&lt;/li&gt;
&lt;/ul&gt;

&lt;p&gt;Now you know the basics of Web Development, where should you go from here? You are literally at a crossroads, if you've enjoyed building the UI or visual part of websites as you've done so far you should continue with step 2, but if you are more drawn to logic than visuals then feel free to skip to step 3.&lt;/p&gt;

&lt;h1&gt;
  
  
  STEP 2: BECOME A FRONTEND GURU
&lt;/h1&gt;

&lt;p&gt;It's time to get into the hamburger of Web Development, making your user interface (UI) better and a lot easier to create. Just kidding, it will be better looking but not easy to create, on the first try. Now you need to learn some more annoyingly awesome technologies.&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;
SASS - Syntactically Awesome Style Sheets&lt;/li&gt;
&lt;/ul&gt;

&lt;p&gt;SASS is a CSS preprocessor/pre-compiler/library or whatever you want to call it. SASS extends some of the features of CSS and makes it feel more like a programming language by providing features such as variables, nesting, partials and functions. It is used for styling websites and is a must-know for front-end developers, at least in my opinion.&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;
BOOTSTRAP&lt;/li&gt;
&lt;/ul&gt;

&lt;p&gt;Well, well, well, let's talk about something that can make your life a lot easier, Bootstrap. Bootstrap is CSS already created for your comfort, meaning you don't have to style your buttons, headings, padding etc from scratch. Just add the bootstrap class to your markup and problem solved. It's something worth learning as it can make your life a whole lot easier and your development work faster.&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;
A FRONTEND FRAMEWORK&lt;/li&gt;
&lt;/ul&gt;

&lt;p&gt;Frontend frameworks allow you to create complicated user interfaces(UI) that you could build with vanilla JavaScript but would be too time-consuming. They do this by providing the developer with reusable code modules. There are a lot of frameworks out there you could choose from, but these are some of the more popular and established ones: React, Vue, Angular and Svelte.&lt;/p&gt;

&lt;p&gt;Now you might just be wondering, which one of these nerds should I choose? Well, that depends on the requirements needed for the job you are applying for or the project you're working on.&lt;/p&gt;

&lt;p&gt;Generally, Svelte is the easiest to learn but not the most stable as it's relatively new, React is intermediate and Angular is the most difficult to learn not for the most terrible reason though. Vue, while having a relatively easy learning curve, also provides high productivity and stability that Svelte currently doesn't have.&lt;/p&gt;

&lt;p&gt;Now you know the basics to become a frontend guru, some other technologies worth researching but not necessary at this stage include:&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;&lt;p&gt;TypeScript&lt;/p&gt;&lt;/li&gt;
&lt;li&gt;&lt;p&gt;Server Side Rendering&lt;/p&gt;&lt;/li&gt;
&lt;li&gt;&lt;p&gt;Static Site Generators&lt;/p&gt;&lt;/li&gt;
&lt;li&gt;&lt;p&gt;The JAM Stack&lt;/p&gt;&lt;/li&gt;
&lt;/ul&gt;

&lt;p&gt;With your knowledge till this point, you can now create your jolly Instagram clone, Twitter clone and other cloneable that never asked to be cloned but are worth cloning because we just enjoy cloning them.&lt;/p&gt;

&lt;h1&gt;
  
  
  STEP 3: BACKEND
&lt;/h1&gt;

&lt;p&gt;Now let's get into the brains of web development. I call it the brains not because the front-end does not involve brains but because... whatever let's just get into it shall we?&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;
SERVER-SIDE TECHNOLOGY AND FRAMEWORK&lt;/li&gt;
&lt;/ul&gt;

&lt;p&gt;This can range from Python to Java. Here you've got to know a programming language and a framework for manipulating the backend of your web app. So I'm gonna leave you with a merry list of programming languages and their preferred frameworks for backend web development.&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;&lt;p&gt;Node.JS - Express&lt;/p&gt;&lt;/li&gt;
&lt;li&gt;&lt;p&gt;Python - Django &amp;amp; Flask&lt;/p&gt;&lt;/li&gt;
&lt;li&gt;&lt;p&gt;Java - Spring MVC&lt;/p&gt;&lt;/li&gt;
&lt;li&gt;&lt;p&gt;Ruby - Ruby on Rails&lt;/p&gt;&lt;/li&gt;
&lt;li&gt;&lt;p&gt;PHP - Laravel&lt;/p&gt;&lt;/li&gt;
&lt;li&gt;&lt;p&gt;C# - ASP.NET&lt;/p&gt;&lt;/li&gt;
&lt;li&gt;&lt;p&gt;Kotlin - Javalin, kTor&lt;/p&gt;&lt;/li&gt;
&lt;/ul&gt;

&lt;p&gt;You could pick one of these languages, learn its basics and get on with a backend framework of its own. None is better than the other. Dear, just pick a language you are comfortable with and get on with its dummy framework.&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;
DATABASES:&lt;/li&gt;
&lt;/ul&gt;

&lt;p&gt;Well, well, your web app can't possibly be complete without being able to store data, manipulate data, present data and eat data too. This is where databases come in as they can make organizing, storing, updating and deleting data a whole lot easier than trying to understand the logic behind Spongebob SquarePants, I mean how can there be a Fire Department under the sea? Sorry, I digress. Anyway, there are majorly two kinds of databases you've got to worry about now:&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;
SQL DATABASES&lt;/li&gt;
&lt;/ul&gt;

&lt;p&gt;SQL(Structured Query Language) databases allow you as a developer, coder, and software engineer, man there are so many names for us these days, to store data in tables and create relationships between them. SQL databases are used in the Finance industry as well as other industries such as Music and Social Media. Examples of SQL databases include PostgreSQL, MySQL, Oracle Database etc.&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;
NO-SQL DATABASES&lt;/li&gt;
&lt;/ul&gt;

&lt;p&gt;Like the name implies, No-SQL databases&lt;/p&gt;

&lt;p&gt;are Non-SQL. Unlike SQL databases, they store data in a JSON (JavaScript Object Notation) format which looks like objects in JavaScript and dictionaries in Python. No-SQL databases provide more flexibility than SQL databases. No-SQL databases are great for gaming, social media, the Internet of Things (IoT) etc. An example of a No-SQL database and the most popular of them all is MongoDB.&lt;/p&gt;

&lt;p&gt;Now that you've gotten your head around databases you might just be wondering which is better. The answer is actually up to you, depending on what you want to build you have to find the suitable database type for your project.&lt;/p&gt;

&lt;p&gt;Before wrapping up this lengthy section, there are some technologies that I think are worth looking into to become a better developer and you should look them up, but again it's totally up to you:&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;&lt;p&gt;REST API&lt;/p&gt;&lt;/li&gt;
&lt;li&gt;&lt;p&gt;GraphQL&lt;/p&gt;&lt;/li&gt;
&lt;li&gt;&lt;p&gt;Docker&lt;/p&gt;&lt;/li&gt;
&lt;li&gt;&lt;p&gt;Jenkins&lt;/p&gt;&lt;/li&gt;
&lt;li&gt;&lt;p&gt;Kubernetes&lt;/p&gt;&lt;/li&gt;
&lt;li&gt;&lt;p&gt;Vector Databases&lt;/p&gt;&lt;/li&gt;
&lt;li&gt;&lt;p&gt;Artificial Intelligence&lt;/p&gt;&lt;/li&gt;
&lt;/ul&gt;

&lt;p&gt;So there you have it, a complete web-developer roadmap that is easy to read and yet completely difficult to stick to, even for myself, because every new technology out there is super exciting and tempting to dabble with. I'll be leaving you with the words of an ancient wise developer on YouTube who said "You don't have to learn every new technology out there".&lt;/p&gt;

&lt;p&gt;I'm not saying be stagnant and not learn new stuff, 'cos that's what we signed up to do as developers, but if you find yourself having a "knowledge overload" and the whole development process becoming a burden then stop and breathe and try to find the balance, I know you will.&lt;/p&gt;

</description>
    </item>
    <item>
      <title>How to Work with Python Lists</title>
      <dc:creator>Favour George</dc:creator>
      <pubDate>Sat, 15 Jul 2023 20:31:05 +0000</pubDate>
      <link>https://dev.to/psycode99/how-to-work-with-python-lists-fo3</link>
      <guid>https://dev.to/psycode99/how-to-work-with-python-lists-fo3</guid>
      <description>&lt;p&gt;Lists are one of the basic data types in programming that allow programmers to represent a finite number of items. In this article, we'll discuss their importance and how to use them effectively in the Python programming language.&lt;/p&gt;

&lt;h2&gt;
  
  
  Table Of Content:
&lt;/h2&gt;

&lt;ul&gt;
&lt;li&gt;&lt;p&gt;What are lists?&lt;/p&gt;&lt;/li&gt;
&lt;li&gt;&lt;p&gt;Uses of Lists&lt;/p&gt;&lt;/li&gt;
&lt;li&gt;&lt;p&gt;Basic Operations on Lists&lt;/p&gt;&lt;/li&gt;
&lt;/ul&gt;

&lt;p&gt;&lt;strong&gt;Prerequisites&lt;/strong&gt; : Knowledge of the Python programming language is crucial.&lt;/p&gt;

&lt;h1&gt;
  
  
  What are Lists?
&lt;/h1&gt;

&lt;p&gt;In computer science, a list or sequence is an abstract data type that represents a finite number of ordered values, where the same value may occur more than once. -&lt;a href="https://en.m.wikipedia.org/wiki/List_(abstract_data_type)"&gt;Wikipedia&lt;/a&gt;&lt;/p&gt;

&lt;p&gt;Lists aid programmers to represent a finite number of items of the same data type together.&lt;/p&gt;

&lt;h1&gt;
  
  
  Uses of Lists
&lt;/h1&gt;

&lt;ul&gt;
&lt;li&gt;&lt;p&gt;&lt;strong&gt;Storing and Organizing Data:&lt;/strong&gt; Lists are used to store data of the same data type together as a collection. With the aid of lists, one can store items of the same type together such as strings, integers and objects.&lt;/p&gt;&lt;/li&gt;
&lt;li&gt;&lt;p&gt;&lt;strong&gt;Storing Temporary Data:&lt;/strong&gt; Lists are useful for storing data that isn't going to be needed for future use but is essential for calculations at the moment.&lt;/p&gt;&lt;/li&gt;
&lt;li&gt;&lt;p&gt;&lt;strong&gt;Iteration over items:&lt;/strong&gt; If the need comes to iterate over items, a list is a great way to store such items as lists are iterable.&lt;/p&gt;&lt;/li&gt;
&lt;/ul&gt;

&lt;h1&gt;
  
  
  Basic Operations on Lists
&lt;/h1&gt;

&lt;p&gt;These are some of the basic operations done on lists in Python&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;
Creating a List&lt;/li&gt;
&lt;/ul&gt;

&lt;p&gt;Creating a list isn't as hard as one would expect.&lt;/p&gt;

&lt;p&gt;The code below creates a list of fruits&lt;/p&gt;

&lt;p&gt;&lt;a href="https://res.cloudinary.com/practicaldev/image/fetch/s--NPQzJ8a5--/c_limit%2Cf_auto%2Cfl_progressive%2Cq_auto%2Cw_800/https://cdn.hashnode.com/res/hashnode/image/upload/v1689450556406/d76665ed-dd67-4157-b08c-daa4830a8d05.png" class="article-body-image-wrapper"&gt;&lt;img src="https://res.cloudinary.com/practicaldev/image/fetch/s--NPQzJ8a5--/c_limit%2Cf_auto%2Cfl_progressive%2Cq_auto%2Cw_800/https://cdn.hashnode.com/res/hashnode/image/upload/v1689450556406/d76665ed-dd67-4157-b08c-daa4830a8d05.png" alt="" width="762" height="484"&gt;&lt;/a&gt;&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;
&lt;strong&gt;Accessing Items in a List&lt;/strong&gt;
&lt;/li&gt;
&lt;/ul&gt;

&lt;p&gt;To access items on a list, one has to specify the index of the item in the list. Indexes work as numbers to show the position of an item in a list, exactly as it works with lists in real life. Take the list below for example:&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;&lt;p&gt;Apple&lt;/p&gt;&lt;/li&gt;
&lt;li&gt;&lt;p&gt;Banana&lt;/p&gt;&lt;/li&gt;
&lt;li&gt;&lt;p&gt;Cherry&lt;/p&gt;&lt;/li&gt;
&lt;/ul&gt;

&lt;p&gt;The item at index 1 or number 1 is Apple. It works almost the same way in programming except that we start counting from 0 instead of 1. So referring to the same list above programmatically, the item at index 1 or number 1 is Banana while Apple is the item at index 0. Let's show that with code as seen below&lt;/p&gt;

&lt;p&gt;&lt;a href="https://res.cloudinary.com/practicaldev/image/fetch/s--rapL6Jsj--/c_limit%2Cf_auto%2Cfl_progressive%2Cq_auto%2Cw_800/https://cdn.hashnode.com/res/hashnode/image/upload/v1689451159103/0e950cca-0a59-4ed0-80b7-0206251ea367.png" class="article-body-image-wrapper"&gt;&lt;img src="https://res.cloudinary.com/practicaldev/image/fetch/s--rapL6Jsj--/c_limit%2Cf_auto%2Cfl_progressive%2Cq_auto%2Cw_800/https://cdn.hashnode.com/res/hashnode/image/upload/v1689451159103/0e950cca-0a59-4ed0-80b7-0206251ea367.png" alt="" width="762" height="632"&gt;&lt;/a&gt;&lt;/p&gt;

&lt;p&gt;&lt;a href="https://res.cloudinary.com/practicaldev/image/fetch/s--EA4jupPv--/c_limit%2Cf_auto%2Cfl_progressive%2Cq_auto%2Cw_800/https://cdn.hashnode.com/res/hashnode/image/upload/v1689451174253/b87bac9f-dc82-475b-b66e-1127e6d87313.png" class="article-body-image-wrapper"&gt;&lt;img src="https://res.cloudinary.com/practicaldev/image/fetch/s--EA4jupPv--/c_limit%2Cf_auto%2Cfl_progressive%2Cq_auto%2Cw_800/https://cdn.hashnode.com/res/hashnode/image/upload/v1689451174253/b87bac9f-dc82-475b-b66e-1127e6d87313.png" alt="" width="762" height="484"&gt;&lt;/a&gt;&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;
Changing Items of a List&lt;/li&gt;
&lt;/ul&gt;

&lt;p&gt;To change an item in a list, we simply access the index of the particular item we wish to change and assign it a different value as shown below:&lt;/p&gt;

&lt;p&gt;&lt;a href="https://res.cloudinary.com/practicaldev/image/fetch/s--whpr_T5C--/c_limit%2Cf_auto%2Cfl_progressive%2Cq_auto%2Cw_800/https://cdn.hashnode.com/res/hashnode/image/upload/v1689451333004/8dd5a71a-de21-4133-8ac4-9dc8418098da.png" class="article-body-image-wrapper"&gt;&lt;img src="https://res.cloudinary.com/practicaldev/image/fetch/s--whpr_T5C--/c_limit%2Cf_auto%2Cfl_progressive%2Cq_auto%2Cw_800/https://cdn.hashnode.com/res/hashnode/image/upload/v1689451333004/8dd5a71a-de21-4133-8ac4-9dc8418098da.png" alt="" width="762" height="484"&gt;&lt;/a&gt;&lt;/p&gt;

&lt;p&gt;In the code above we changed the value of the fruit at index 1 from banana to orange and this is reflected in the output below&lt;/p&gt;

&lt;p&gt;&lt;a href="https://res.cloudinary.com/practicaldev/image/fetch/s--zYOf1VrC--/c_limit%2Cf_auto%2Cfl_progressive%2Cq_auto%2Cw_800/https://cdn.hashnode.com/res/hashnode/image/upload/v1689450845025/835b2139-1433-4da3-94e3-44bbe6a274cc.png" class="article-body-image-wrapper"&gt;&lt;img src="https://res.cloudinary.com/practicaldev/image/fetch/s--zYOf1VrC--/c_limit%2Cf_auto%2Cfl_progressive%2Cq_auto%2Cw_800/https://cdn.hashnode.com/res/hashnode/image/upload/v1689450845025/835b2139-1433-4da3-94e3-44bbe6a274cc.png" alt="" width="762" height="410"&gt;&lt;/a&gt;&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;
Removing Items from a List&lt;/li&gt;
&lt;/ul&gt;

&lt;p&gt;To remove an item from a list we use the remove() method and specify within the method the particular item we wish to remove from the list as shown below:&lt;/p&gt;

&lt;p&gt;&lt;a href="https://res.cloudinary.com/practicaldev/image/fetch/s--rPAY381Q--/c_limit%2Cf_auto%2Cfl_progressive%2Cq_auto%2Cw_800/https://cdn.hashnode.com/res/hashnode/image/upload/v1689450884822/8bdf8f64-1098-40d2-8bbf-82a2785528ab.png" class="article-body-image-wrapper"&gt;&lt;img src="https://res.cloudinary.com/practicaldev/image/fetch/s--rPAY381Q--/c_limit%2Cf_auto%2Cfl_progressive%2Cq_auto%2Cw_800/https://cdn.hashnode.com/res/hashnode/image/upload/v1689450884822/8bdf8f64-1098-40d2-8bbf-82a2785528ab.png" alt="" width="762" height="484"&gt;&lt;/a&gt;&lt;/p&gt;

&lt;p&gt;&lt;a href="https://res.cloudinary.com/practicaldev/image/fetch/s--Q4CIp_ET--/c_limit%2Cf_auto%2Cfl_progressive%2Cq_auto%2Cw_800/https://cdn.hashnode.com/res/hashnode/image/upload/v1689450904450/78106121-314d-4f44-9613-246b7ddff1c7.png" class="article-body-image-wrapper"&gt;&lt;img src="https://res.cloudinary.com/practicaldev/image/fetch/s--Q4CIp_ET--/c_limit%2Cf_auto%2Cfl_progressive%2Cq_auto%2Cw_800/https://cdn.hashnode.com/res/hashnode/image/upload/v1689450904450/78106121-314d-4f44-9613-246b7ddff1c7.png" alt="" width="762" height="410"&gt;&lt;/a&gt;&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;
Adding Items to a List&lt;/li&gt;
&lt;/ul&gt;

&lt;p&gt;To add a new item to a list, we simply use the append() method that lists have in Python and inside the method we provide the item we wish to add to the list as shown below:&lt;/p&gt;

&lt;p&gt;&lt;a href="https://res.cloudinary.com/practicaldev/image/fetch/s--FkexkeOi--/c_limit%2Cf_auto%2Cfl_progressive%2Cq_auto%2Cw_800/https://cdn.hashnode.com/res/hashnode/image/upload/v1689450941650/668648ea-b9fc-472f-9fba-6851ae3d0848.png" class="article-body-image-wrapper"&gt;&lt;img src="https://res.cloudinary.com/practicaldev/image/fetch/s--FkexkeOi--/c_limit%2Cf_auto%2Cfl_progressive%2Cq_auto%2Cw_800/https://cdn.hashnode.com/res/hashnode/image/upload/v1689450941650/668648ea-b9fc-472f-9fba-6851ae3d0848.png" alt="" width="762" height="484"&gt;&lt;/a&gt;&lt;/p&gt;

&lt;p&gt;It's important to note that the append method adds an item to the end of the list.&lt;/p&gt;

&lt;p&gt;&lt;a href="https://res.cloudinary.com/practicaldev/image/fetch/s--7lAT3Qy3--/c_limit%2Cf_auto%2Cfl_progressive%2Cq_auto%2Cw_800/https://cdn.hashnode.com/res/hashnode/image/upload/v1689450966936/035d05f7-de59-41a0-8378-6508691fd40e.png" class="article-body-image-wrapper"&gt;&lt;img src="https://res.cloudinary.com/practicaldev/image/fetch/s--7lAT3Qy3--/c_limit%2Cf_auto%2Cfl_progressive%2Cq_auto%2Cw_800/https://cdn.hashnode.com/res/hashnode/image/upload/v1689450966936/035d05f7-de59-41a0-8378-6508691fd40e.png" alt="" width="762" height="410"&gt;&lt;/a&gt;&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;
Sorting a List&lt;/li&gt;
&lt;/ul&gt;

&lt;p&gt;We can sort lists by using the sort() method on the list we intend to sort. This method will sort the list in ascending order by default, but if we set the reverse keyword argument to True, we can sort a list in descending order as well. Let's see the code for this below:&lt;/p&gt;

&lt;p&gt;&lt;a href="https://res.cloudinary.com/practicaldev/image/fetch/s--bkdEXCUo--/c_limit%2Cf_auto%2Cfl_progressive%2Cq_auto%2Cw_800/https://cdn.hashnode.com/res/hashnode/image/upload/v1689451006797/9960b10d-9295-4123-bc6b-c8c7e6cb215f.png" class="article-body-image-wrapper"&gt;&lt;img src="https://res.cloudinary.com/practicaldev/image/fetch/s--bkdEXCUo--/c_limit%2Cf_auto%2Cfl_progressive%2Cq_auto%2Cw_800/https://cdn.hashnode.com/res/hashnode/image/upload/v1689451006797/9960b10d-9295-4123-bc6b-c8c7e6cb215f.png" alt="" width="800" height="372"&gt;&lt;/a&gt;&lt;/p&gt;

&lt;p&gt;&lt;a href="https://res.cloudinary.com/practicaldev/image/fetch/s--C3yZMdxR--/c_limit%2Cf_auto%2Cfl_progressive%2Cq_auto%2Cw_800/https://cdn.hashnode.com/res/hashnode/image/upload/v1689451026645/e164b3dd-c6d6-449e-8d93-a23fb0d17f31.png" class="article-body-image-wrapper"&gt;&lt;img src="https://res.cloudinary.com/practicaldev/image/fetch/s--C3yZMdxR--/c_limit%2Cf_auto%2Cfl_progressive%2Cq_auto%2Cw_800/https://cdn.hashnode.com/res/hashnode/image/upload/v1689451026645/e164b3dd-c6d6-449e-8d93-a23fb0d17f31.png" alt="" width="800" height="297"&gt;&lt;/a&gt;&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;
&lt;strong&gt;Clearing a List&lt;/strong&gt;
&lt;/li&gt;
&lt;/ul&gt;

&lt;p&gt;To clear a list means to wipe it of all its contents. To do this we'll use the clear() method on the list we want to clear as shown below&lt;/p&gt;

&lt;p&gt;&lt;a href="https://res.cloudinary.com/practicaldev/image/fetch/s--5Dedq7py--/c_limit%2Cf_auto%2Cfl_progressive%2Cq_auto%2Cw_800/https://cdn.hashnode.com/res/hashnode/image/upload/v1689451060550/6d8d8627-7bde-42a7-93c4-16e84b344efb.png" class="article-body-image-wrapper"&gt;&lt;img src="https://res.cloudinary.com/practicaldev/image/fetch/s--5Dedq7py--/c_limit%2Cf_auto%2Cfl_progressive%2Cq_auto%2Cw_800/https://cdn.hashnode.com/res/hashnode/image/upload/v1689451060550/6d8d8627-7bde-42a7-93c4-16e84b344efb.png" alt="" width="800" height="323"&gt;&lt;/a&gt;&lt;/p&gt;

&lt;p&gt;&lt;a href="https://res.cloudinary.com/practicaldev/image/fetch/s--xBlexf-i--/c_limit%2Cf_auto%2Cfl_progressive%2Cq_auto%2Cw_800/https://cdn.hashnode.com/res/hashnode/image/upload/v1689451095276/aa1052ea-9c26-453c-9600-6d52d063a376.png" class="article-body-image-wrapper"&gt;&lt;img src="https://res.cloudinary.com/practicaldev/image/fetch/s--xBlexf-i--/c_limit%2Cf_auto%2Cfl_progressive%2Cq_auto%2Cw_800/https://cdn.hashnode.com/res/hashnode/image/upload/v1689451095276/aa1052ea-9c26-453c-9600-6d52d063a376.png" alt="" width="762" height="410"&gt;&lt;/a&gt;&lt;/p&gt;

&lt;p&gt;These are but a few operations that can be performed on Python lists. For a more comprehensive guide visit the &lt;a href="https://www.w3schools.com/python/python_lists.asp"&gt;W3School's&lt;/a&gt; website.&lt;/p&gt;

</description>
    </item>
  </channel>
</rss>
