Before starting this tutorial on Exception Handling, we have to know why actually we want to trap(or handle) errors. For the answer, we handle exceptions to deal with the situations like file does not exist, unusual input from users and other problems that can cause our programs to crash. In computer science, there are two distinguishable types of errors : syntax errors and exceptions.
Syntax errors leads to program crash in the compile time whereas Exceptions leads to program crash while running the program. We can conclude Exceptions that whenever the statement or expression of program is syntactically correct, it may cause an error when we execute it.
Now, let's dive into the implementation part that how actually we can handle exceptions in Python. I will be using Python version 3.8.3 (latest version as of writing this post) and VS code as editor.
For the clarification, I will make several python files and try to cover most of the topics.
Traceback (most recent call last): File "divide.py", line 1, in <module> print(7/0) ZeroDivisionError: division by zero
We all know that something number cannot be divided by 0 and its against mathematical rule i.e why python interpreter reported us with the error traceback, ZeroDivisionError. But sometimes, user by mistakenly gave input like this. In order to handle this situation we have to catch the errors. The best way to handle this kind of error is to not show what Python normally shows for this error.
Using try/except blocks
try: insert expression that can generate errors except Exception: catch errors and provide failure information
Let's modify the above code divide.py
try: print(7/0) except ZeroDivisionError: print("Can't divide by zero!")
Can't divide by zero!
Here we successfully handle the ZeroDivisonError and provide the output in more informative way that layman can understood easily rather than before.
Using else block
Upto the point we are now familiar with try, except blocks. There is another optional block called else for try, except statements. Professionals programmers do not keep their whole code into the try block because they want the try block to check conditions whether code executed or not. If conditions not met they catch the errors from the except block. So to keep the code clean and easy to understand and only execute if certain conditons are fulfilled we have to use else block.
The following python file only print the answer of division in the else block if the try block executed successfully.
# take input of two numbers first_number = input('Input First Number: ') second_number = input('Input Second Number: ') try: answer = int(first_number) / int(second_number) except ZeroDivisionError: print("Can't divide by zero!") else: print(first_number + " divide by " + second_number +" is " + str(answer))
Input First Number: 49 Input Second Number: 7 49 divide by 7 is 7.0
Here the else block prints the answer only after try block statements executed otherwise we encountered with ZeroDivisionError.
Using finally block
After the else block there is also another block called finally that will be executed whether an exception occurs or not. This block is executed at last after try-except statements completed.
Let's take an example of opening certain text file named codefires.txt.
try: open('codefires.txt') except FileNotFoundError: print('File cannot be found') else: print('try block conditions satisfied') finally: print('this block is executed whether exception occurs or not')
When we run this program with file named codefires.txt in the working directory, we get output :
try block conditions satisfied this block is executed whether exception occurs or not
Now run the same program file-opener.py without placing file codefires.txt, we get this output:
File cannot be found this block is executed whether exception occurs or not
We can noticed that in both the cases finally block statements executed.