User-defined exceptions allow developers to handle specific error scenarios by creating custom exception classes. These custom classes can be designed to represent unique problems in an application, improving error tracking and making debugging more efficient.
User-defined exceptions are useful when built-in exceptions (like std::runtime_error, std::out_of_range, etc.) are insufficient for handling specific errors in a program. By defining your own exceptions, you can tailor them to represent particular issues relevant to your domain or business logic, such as database errors, file handling issues, or validation failures.
A user-defined exception class typically inherits from a standard C++ exception class like std::exception or its derived classes (std::runtime_error, std::logic_error, etc.). By overriding the what() method, you can provide a custom error message that describes the specific error condition.
std::exception or its subclasses: This ensures the custom exception is compatible with the standard exception-handling mechanism in C++.what() method: The what() method returns an error message, which can be customized to include more detailed and specific information about the error.#include <iostream>
#include <exception>
#include <string>
// Define a custom exception class
class InvalidAgeException : public std::exception {
private:
std::string message;
public:
// Constructor to set the custom error message
InvalidAgeException(const std::string& msg) : message(msg) {}
// Override the what() method to return the custom error message
const char* what() const noexcept override {
return message.c_str();
}
};
int main() {
int age;
std::cout << "Enter your age: ";
std::cin >> age;
try {
// Throw custom exception if age is invalid
if (age < 0) {
throw InvalidAgeException("Error: Age cannot be negative.");
}
std::cout << "Your age is " << age << std::endl;
} catch (const InvalidAgeException& e) {
// Catch and display the custom exception message
std::cerr << "Caught an exception: " << e.what() << std::endl;
}
return 0;
}
InvalidAgeException, allows the program to provide a specific error message when invalid age input is detected.In large applications, you can define multiple user-defined exceptions, each targeting specific error types. For instance, you can create exceptions like FileNotFoundException, InvalidUserInputException, or DatabaseConnectionException to handle distinct issues.
class FileNotFoundException : public std::exception {
public:
const char* what() const noexcept override {
return "Error: File not found.";
}
};
class InvalidInputException : public std::exception {
public:
const char* what() const noexcept override {
return "Error: Invalid input provided.";
}
};
int main() {
try {
// Simulate file not found error
throw FileNotFoundException();
} catch (const std::exception& e) {
std::cerr << e.what() << std::endl;
}
try {
// Simulate invalid input error
throw InvalidInputException();
} catch (const std::exception& e) {
std::cerr << e.what() << std::endl;
}
return 0;
}
std::exception or its derivatives to maintain compatibility with C++’s exception-handling system.In larger applications, custom exception classes can be organized in a hierarchy. For instance, you might have a base exception class like ApplicationException, with subclasses for more specific exceptions like FileException, DatabaseException, etc.
class ApplicationException : public std::exception {
public:
const char* what() const noexcept override {
return "Application encountered an error.";
}
};
class FileException : public ApplicationException {
public:
const char* what() const noexcept override {
return "File error occurred.";
}
};
class NetworkException : public ApplicationException {
public:
const char* what() const noexcept override {
return "Network error occurred.";
}
};