what is Exception Handling?
Exception handling allows you to manage unexpected errors that occur during program execution by using try, except, else, and finally blocks.
Why Use Exception Handling in I/O?
Basic Exception Handling Syntax
try: # Code that might raise an exception risky_operation() except ExceptionType: # Code to handle the exception handle_exception() else: # Code to run if no exception occurs success_operation() finally: # Code that runs no matter what (cleanup actions) cleanup()
Common I/O Errors
- FileNotFoundError: File doesn't exist.
- PermissionError: Insufficient permissions to access the file.
- IsADirectoryError: Tried to open a directory instead of a file.
- IOError: General I/O-related error.
Examples-of-Exception-Handling-During-I/O
1. Reading a File
Example: Gracefully handling the case when a file doesn't exist.
try: with open("nonexistent_file.txt", "r") as file: content = file.read() print(content) except FileNotFoundError: print("Error: The file does not exist.") except PermissionError: print("Error: You do not have permission to read the file.") else: print("File read successfully!") finally: print("Finished file operation.")2. Writing to a File
Example: Handling errors during file writing.
try: with open("output.txt", "w") as file: file.write("Hello, World!") print("Data written to file.") except PermissionError: print("Error: Insufficient permissions to write to the file.") except IOError as e: print(f"An I/O error occurred: {e}") else: print("File written successfully.") finally: print("File operation completed.")3. Using finally for Cleanup
Example: Closing a file explicitly to ensure proper resource management.
file = None try: file = open("example.txt", "r") content = file.read() print(content) except FileNotFoundError: print("Error: File not found.") finally: if file: file.close() print("File closed.")4. Nested Exception Handling
Example: Handling different exceptions separately.
try: filename = "data.txt" mode = "x" # "x" mode creates a file, raises error if file exists with open(filename, mode) as file: file.write("Some data") except FileExistsError: print("Error: The file already exists.") except IOError as e: print(f"General I/O error: {e}") else: print("File written successfully!")5. Catch-All Exception Handling
Example: Using a general except block to catch unexpected exceptions.
try: with open("file.txt", "r") as file: content = file.read() except Exception as e: print(f"An unexpected error occurred: {e}")
Real-Life Scenarios
Scenario 1: Logging ErrorsIf file operations fail, log the error instead of crashing the program.
import logging logging.basicConfig(filename="errors.log", level=logging.ERROR) try: with open("logfile.txt", "r") as file: content = file.read() except Exception as e: logging.error(f"An error occurred: {e}")Scenario 2: Retry Logic
Retry a file operation a limited number of times if it fails.
import time retries = 3 for attempt in range(retries): try: with open("important_data.txt", "r") as file: print(file.read()) break except FileNotFoundError: print(f"Attempt {attempt + 1}: File not found. Retrying...") time.sleep(1) except Exception as e: print(f"An error occurred: {e}") break else: print("Failed after multiple attempts.")Scenario 3: Processing Multiple Files
Handle errors for individual files without halting the entire operation.
files = ["file1.txt", "file2.txt", "file3.txt"] for file_name in files: try: with open(file_name, "r") as file: print(f"Contents of {file_name}:") print(file.read()) except FileNotFoundError: print(f"Error: {file_name} not found.") except Exception as e: print(f"Error while processing {file_name}: {e}")
Best Practices
1. Use Specific Exceptions:Catch only the exceptions you expect, like FileNotFoundError, rather than a generic Exception.
2. Use Context Managers (with Statement):Automatically handles file closing.
Example: with open("file.txt", "r") as file:3. Log Errors Instead of Printing:
Use the logging module for better error tracking.
4. Avoid Silencing Exceptions:o Catch and handle exceptions meaningfully instead of suppressing them.
5. Use finally for Cleanup:o Ensure resources like file handles are released.
Summary
• What You Learned:o Python's exception handling mechanism (try, except, finally) is crucial for robust I/O operations.
o Handle specific I/O errors like FileNotFoundError, PermissionError, and IOError.
o Reading from and writing to files.
o Logging and retry mechanisms.
o Handling multiple files gracefully.