Python3 Errors Execptions
# Python3 Errors and Exceptions
## Python3.x Python3 Errors and Exceptions
As a Python beginner, when you start learning Python programming, you will often see some error messages. We did not mention them earlier, but this chapter will introduce them specifically.
Python has two types of errors that are easy to identify: syntax errors and exceptions.
Python's `assert` (assertion) is used to evaluate an expression and triggers an exception when the expression condition is false.
!(https://static.jyshare.com/images/mix/assets-py.webp)
## Syntax Errors
Python's syntax errors, also known as parsing errors, are common for beginners. For example:
>>>while True print('Hello world')
File "", line 1,in ?
while True print('Hello world')
^
SyntaxError: invalid syntax
In this example, the function `print()` is found to have an error because it is missing a colon `:` before it.
The syntax parser points out the line with the error and marks the first detected error with a small arrow.
## Exceptions
Even if a Python program's syntax is correct, errors may still occur when it is run. Errors detected during runtime are called exceptions.
Most exceptions are not handled by the program and are displayed here as error messages:
## Example
>>>10 * (1/0)# 0 cannot be a divisor, triggering an exception
Traceback (most recent call last):
File "", line 1,in ?
ZeroDivisionError: division by zero
>>>4 + spam*3# spam is undefined, triggering an exception
Traceback (most recent call last):
File "", line 1,in ?
NameError: name 'spam'is not defined
>>>'2' + 2# int cannot be added to str, triggering an exception
Traceback (most recent call last):
File "", line 1,in
TypeError: can only concatenate str(not"int") to str
Exceptions appear in different types, and these types are printed as part of the information. The types in the examples are `ZeroDivisionError`, `NameError`, and `TypeError`.
The front part of the error message shows the context where the exception occurred and displays specific information in the form of a call stack.
## Exception Handling
### try/except
Exception catching can be done using the `try/except` statement.
!(#)
In the following example, the user is asked to enter a valid integer, but the user is allowed to interrupt the program (using Control-C or the method provided by the operating system). The user interruption message will trigger a `KeyboardInterrupt` exception.
while True:
try:
x =int(input("Please enter a number: "))
break
except ValueError:
print("That's not a valid number. Please try again!")
The `try` statement works as follows:
* First, the `try` clause (the statement between the keyword `try` and the keyword `except`) is executed.
* If no exception occurs, the `except` clause is skipped, and the `try` clause execution ends.
* If an exception occurs during the execution of the `try` clause, the rest of the `try` clause is skipped. If the exception type matches the name after `except`, the corresponding `except` clause is executed.
* If an exception does not match any `except`, it is passed to the upper-level `try`.
A `try` statement may contain multiple `except` clauses to handle different specific exceptions. At most, only one branch will be executed.
The handler will only handle exceptions in the corresponding `try` clause, not exceptions in other `try` handlers.
An `except` clause can handle multiple exceptions at once. These exceptions are placed in parentheses to form a tuple, for example:
except(RuntimeError,TypeError,NameError):
pass
The last `except` clause can omit the exception name; it will be used as a wildcard. You can use this method to print an error message and then re-raise the exception.
import sys
try:
f =open('myfile.txt')
s = f.readline()
i =int(s.strip())
except OSError as err:
print("OS error: {0}".format(err))
except ValueError:
print("Could not convert data to an integer.")
except:
print("Unexpected error:",sys.exc_info())
raise
### try/except...else
The `try/except` statement also has an optional **else** clause. If used, it must be placed after all `except` clauses.
The `else` clause is executed when no exception occurs in the `try` clause.
!(#)
The following example checks whether a file can be opened in the `try` statement. If the file opens normally without any exception, the `else` part is executed to read the file contents:
for arg in sys.argv[1:]:
try:
f =open(arg,'r')
except IOError:
print('cannot open', arg)
else:
print(arg,'has',len(f.readlines()),'lines')
f.close()
Using the `else` clause is better than putting all statements inside the `try` clause, as it avoids catching unexpected exceptions that `except` cannot handle.
Exception handling not only handles exceptions that occur directly in the `try` clause but also handles exceptions raised in functions called within the clause (even indirectly). For example:
>>>def this_fails():
x =1/0
>>>try:
this_fails()
except ZeroDivisionError as err:
print('Handling run-time error:', err)
Handling run-time error: int division or modulo by zero
### try-finally Statement
The `try-finally` statement executes the final code regardless of whether an exception occurs.
!(#)
In the following example, the `finally` clause is executed whether an exception occurs or not:
## Example
try:
()
except AssertionError as error:
print(error)
else:
try:
with open('file.log')as file:
read_data =file.read()
except FileNotFoundError as fnf_error:
print(fnf_error)
finally:
print('This message will be printed regardless of whether an exception occurred.')
* * *
## Raising Exceptions
Python uses the `raise` statement to raise a specified exception.
The syntax for `raise` is as follows:
raise [Exception [, args [, traceback]]]
!(#)
The following example raises an exception if `x` is greater than 5:
x =10
if x >5:
raise Exception('x cannot be greater than 5. The value of x is: {}'.format(x))
Executing the above code will trigger an exception:
Traceback (most recent call last): File "test.py", line 3, in raise Exception('x cannot be greater than 5. The value of x is: {}'.format(x))Exception: x cannot be greater than 5. The value of x is: 10
The sole argument to `raise` specifies the exception to be raised. It must be an instance of an exception or an exception class (i.e., a subclass of `Exception`).
If you only want to know whether an exception was raised without handling it, a simple `raise` statement can re-raise it.
>>>try:
raise NameError('HiThere')# Simulate an exception.
except NameError:
print('An exception flew by!')
raise
An exception flew by!
Traceback (most recent call last):
File "", line 2,in ?
NameError: HiThere
* * *
## User-Defined Exceptions
You can create your own exceptions by creating a new exception class. Exception classes inherit from the `Exception` class, either directly or indirectly, for example:
>>>class MyError(Exception):
def __init__ (self, value):
self.value= value
def __str__ (self):
return repr(self.value)
>>>try:
raise MyError(2*2)
except MyError as e:
print('My exception occurred, value:', e.value)
My exception occurred, value: 4
>>>raise MyError('oops!')
Traceback (most recent call last):
File "", line 1,in ?
__main__ .MyError: 'oops!'
In this example, the default `__init__()` of the `Exception` class is overridden.
When creating a module that may raise multiple different exceptions, a common practice is to establish a base exception class for the package and then create different subclasses for different error conditions based on this base class:
class Error(Exception):
"""Base class for exceptions in this module."""
pass
class InputError(Error):
"""Exception raised for errors in the input.
Attributes:
expression -- input expression in which the error occurred
message -- explanation of the error
"""
def __init__ (self, expression, message):
self.expression= expression
self.message= message
class TransitionError(Error):
"""Raised when an operation attempts a state transition that's not
allowed.
Attributes:
previous -- state at beginning of transition
next -- attempted new state
message -- explanation of why the specific transition is not allowed
"""
def __init__ (self, previous, next, message):
self.previous= previous
self.next= next
self.message= message
Most exception names end with "Error," similar to standard exception naming.
* * *
## Defining Cleanup Actions
The `try` statement has another optional clause that defines cleanup actions that will be executed under any circumstances. For example:
>>>try:
... raise KeyboardInterrupt
... finally:
... print('Goodbye, world!')
...
Goodbye, world!
Traceback (most recent call last):
File "", line 2,in
KeyboardInterrupt
In the above example, the `finally` clause is executed regardless of whether an exception occurs in the `try` clause.
If an exception is raised in the `try` clause (or in the `except` and `else` clauses) and is not caught by any `except`, the exception will be re-raised after the `finally` clause is executed.
Here is a more complex example (containing both `except` and `finally` clauses in the same `try` statement):
>>>def divide(x, y):
try:
result = x / y
except ZeroDivisionError:
print("division by zero!")
else:
print("result is", result)
finally:
print("executing finally clause")
>>> divide(2,1)
result is 2.0
executing finally clause
>>> divide(2,0)
division by zero!
executing finally clause
>>> divide("2","1")
executing finally clause
Traceback (most recent call last):
File "", line 1,in ?
File "", line 3,in divide
TypeError: unsupported operand type(s)for /: 'str'and'str'
* * *
## Predefined Cleanup Actions
Some objects define standard cleanup actions that will be executed once they are no longer needed, regardless of whether the system successfully used them.
The following example demonstrates trying to open a file and print its contents to the screen:
for line in open("myfile.txt"):
print(line, end="")
The problem with this code is that after execution, the file remains open and is not closed.
The `with` statement ensures that objects like files will correctly execute their cleanup methods after use:
with open("myfile.txt")as f:
for line in f:
print(line, end="")
After this code executes, the file `f` will always be closed, even if a problem occurs during processing.
For more information on the `with` keyword, refer to: (#)
* * *
## Related Content
[Python assert (Assertion)](#)
(#)
YouTip