3. python_exception handling

Posted by firstcoastshopping on Wed, 21 Aug 2019 04:05:28 +0200

3. Exceptions:

python uses special objects called exceptions to manage errors that occur during program execution.

Whenever an error occurs that confuses Python, it creates an exception object.If you write code to handle the exception, the program will continue to run;

If you do not handle the exception, the program stops and displays a traceback containing a report of the exception.

Exceptions are handled using try-except code blocks.The try-except code block lets Python perform the specified action and tells Python what to do if an exception occurs.When you use try-except code blocks, the program will continue to run even if there are exceptions: show friendly error messages you write, not traceback that confuses users.

3.1. Handle ZeroDivisionError exceptions:

Example 1: division.py

print(5/0)

#Report errors:
Traceback (most recent call last):
    File "division.py", line 1, in < module > 
    	print( 5/ 0)
❶ ZeroDivisionError: division by zero

Procedural analysis:

ZeroDivisionError is an exception object.This object is created when python can't do what you want; we can modify the program based on this information.

3.2. Use try-except code block:

When you think an error may have occurred, you can write a try-except code block to handle the exception that may have been thrown.You let Python try to run some code and tell it what to do if it raises a specified exception.

Example 2:

try:
    print(5/0)
except ZeroDivisionError:
    print("You can't dvide by zero!")

Procedural analysis:

We put the line of code that caused the error, print(5/0), in a try block of code.

If the code in the try code block runs fine, python skips the except code block.

If the code in the try code block causes an error, python will look for such an except code block and run the code in it, that is, the error specified is the same as the error raised.

If there is additional code behind the try-except code block, the program will then run the following code.

3.3. Use abnormalities to avoid galloping:

When errors occur, it is especially important to handle them properly if the program still has work to do.This often occurs when a program that requires the user to provide input handles invalid input appropriately and prompts the user to provide valid input without crashing.

Example 3, division.py: Create a simple calculator that performs division operations only:

print(" Give me two numbers, and I'll divide them.") 
print(" Enter 'q' to quit.") 
while True: 
    ❶ first_number = input("\ nFirst number: ")
    if first_number = = 'q': 
        break 
    ❷ second_number = input(" Second number: ")
    if second_number = = 'q':
        break
    ❸ answer = int( first_number) / int( second_number)
    print( answer)

Procedural analysis:

This program does not take any action to handle errors, so it will crash when it is asked to perform a divide-by-zero start operation.

#Program output:
Give me two numbers, and I'll divide them. 
Enter 'q' to quit.
First number: 5
Second number: 0
Traceback (most recent call last):
	File "division.py", line 9, in < module >
    	answer = int( first_number) / int( second_number) ZeroDivisionError: division by zero

Disadvantages of a program crash:

  1. Users who don't know the technology are confused by them, and if a user has malicious intent, he or she will use traceback to get information you don't want them to know.
  2. He will know the name of your program file and will see some code that doesn't work correctly.
  3. Sometimes a well-trained attacker can use this information to determine what kind of attack can be launched on your code.

3.4, else code block:

By placing code that may cause errors in the try-except code block, you can improve the program's ability to withstand errors.

Example 4. The following example also contains an else code block; code that depends on the successful execution of the try code block should be placed in the else code block:

print(" Give me two numbers, and I'll divide them.")
print(" Enter 'q' to quit.") 
while True: 
    first_number = input("\n First number: ")
    if first_number = = 'q': 
        break
    second_number = input(" Second number: ")try: 
        answer = int( first_number) / int( second_number)except ZeroDivisionError:
            print(" You can't divide by 0!")else:
            print( answer)
            
#Output results:
Give me two numbers, and I'll divide them.
Enter 'q' to quit.
First number: 5 
Second number: 0 
You can't divide by 0!

First number: 5 
Second number: 2 
2.5 
First number: q

The try-except-else code block works as follows:

  1. python tries to execute code in the try block, and only code that may throw an exception needs to be placed in the try statement.
  2. Sometimes, there are some codes that need to be run only if the try code block executes successfully; these codes should be placed in the else code block.
  3. The except code tells python what to do if it attempts to run code in the try code block that raises a specified exception.
  4. By predicting code that might be wrong, robust programs can be written that can continue to run even in the face of invalid data or lack of resources, thereby protecting against unintentional user errors and malicious attacks.

3.5. Handle FileNotFoundError exception:

A common problem when working with files is that they cannot be found: the file you are looking for may be somewhere else, the file name may be incorrect, or the file does not exist at all.In this case, try-except code blocks can be used to process this in an intuitive way.

Example 5: alice.py

filename = 'alice.txt'

with open(filename) as f_obj:
    contents = f_obj.read()
    
#Exception thrown when Python cannot read a file that does not exist:
Traceback (most recent call last):
    File "alice.py", line 3, in < module > 
    	with open( filename) as f_obj: 
FileNotFoundError: [Errno 2] No such file or directory: 'alice.txt'

try-except exception improvement:

filename = 'alice.txt'

try:
	with open(filename) as f_obj:
        contents = f_obj.read()
except FileNotFoundError:
    msg = "Sorry,the file " + filename + "does not exist."
    print(msg)

If the file does not exist, the program does nothing, so error handling code makes little sense.

Let's expand on this example to see how exception handling can help you when you're working with multiple files.

3.6. Analytical Text:

Method split(), which splits a string into parts with a space separator and stores them in a list.

title = "Alice in wonderland"
title.split()
['Alice','in','wonderland']

To calculate how many words the novel book.txt contains, we will call split() on the whole story and calculate how many elements the list contains to determine how many words the whole book roughly contains:

Example 6:

filename = 'book.txt'

try:
    with open(filename,encoding = "UTF-8") as f_obj:
        content = f_obj.read()
except FileNotFoundError:
    msg = "Sorry,the file " + filename + " does not exist."
    print(msg)
else:
    #Calculate the approximate number of words in the file
    words = contents.split()
    num_worlds = len(words)
    print("The file " + filename + " has about " + str(num_words) + " words.")

3.7. Use multiple files:

Example 7: word_count.py

def count_words(filename):
    """Calculate the approximate number of words in a file"""
    try:
        with open(filename) as f_obj:
            contents = f_obj.read()
        except FileNotFoundError:
            msg = "Sorry,the file " + filename + " does not exist."
            print(msg)
    else:
        #Calculate the approximate number of words in the file
        words = content.split()
        num_words = len(words)
        print("The file " + filename + " has about " + str(num_words) + " words.")

filename = 'book.txt'
count_worlds(filename)

filenames = ['alice.txt','siddhartha.txt','moby_dick.txt','little_women.txt']
for filename in filenames:
    count_words(filename)
    
#Output results:
The file alice.txt has about 29461 words.
Sorry, the file siddhartha.txt does not exist. 
The file moby_dick.txt has about 215136 words. 
The file little_women.txt has about 189079 words.

3.8. Keep silent when failing:

The pass statement in Python, which can be used in the code block to let Python do nothing.

def count_words( filename):
    """ Calculate the approximate number of words in a file""" 
    try:
        --snip-- 
    except FileNotFoundError:pass
    else: 
        --snip-- 
filenames = [' alice.txt', 'siddhartha.txt', 'moby_dick.txt', 'little_women.txt']
for filename in filenames: 
    count_words( filename)
    
#Output results:
The file alice.txt has about 29461 words. The file moby_dick.txt has about 215136 words. The file little_women.txt has about 189079 words.

The pass statement also acts as a placeholder, reminding you that you haven't done anything somewhere in the program, and that you might want to do something here in the future.

3.9. Decide to report those errors:

  1. python's error handling structure allows you to carefully control how much error information users share, and how much information you want to share is up to you.
  2. Well-written, well-tested code is not prone to internal errors, but exceptions can occur as long as the program relies on external factors such as user input, the presence of specified files, and network links.
  3. Experience can tell where the program contains exception handling blocks and how much information to provide users when an error occurs.

The code examples in this chapter come from: [US] Eric Matthes. Python programming: from getting started to practice

Topics: Python calculator encoding network