Правильный способ наследования из std:: exception
Я только что создал иерархию исключений и хотел передать char*
конструктору одного из моих производных классов с сообщением о том, что неправильно, но, по-видимому, std::exception
не имеет конструктора, который позволил бы мне это сделать. Тем не менее есть член класса what()
, который предполагает, что некоторая информация может быть передана.
Как я могу (могу ли я?) Передать текст производному классу a std::exception
, чтобы передать информацию моему классу исключений, поэтому я могу сказать где-то в коде:
throw My_Exception("Something bad happened.");
Ответы
Ответ 1
Если вы хотите использовать конструктор строк, вы должны наследовать от std:: runtime_error или std:: logic_error, который реализует конструктор строк и реализует std:: exception:: какой метод.
Тогда это просто случай вызова конструктора runtime_error/logic_error из вашего нового унаследованного класса, или если вы используете С++ 11, вы можете использовать наследование конструктора.
Ответ 2
Я использую следующий класс для своих исключений, и он отлично работает:
class Exception: public std::exception
{
public:
/** Constructor (C strings).
* @param message C-style string error message.
* The string contents are copied upon construction.
* Hence, responsibility for deleting the char* lies
* with the caller.
*/
explicit Exception(const char* message):
msg_(message)
{
}
/** Constructor (C++ STL strings).
* @param message The error message.
*/
explicit Exception(const std::string& message):
msg_(message)
{}
/** Destructor.
* Virtual to allow for subclassing.
*/
virtual ~Exception() throw (){}
/** Returns a pointer to the (constant) error description.
* @return A pointer to a const char*. The underlying memory
* is in posession of the Exception object. Callers must
* not attempt to free the memory.
*/
virtual const char* what() const throw (){
return msg_.c_str();
}
protected:
/** Error message.
*/
std::string msg_;
};
Ответ 3
Как насчет этого:
class My_Exception : public std::exception
{
public:
virtual char const * what() const { return "Something bad happend."; }
};
Или создайте конструктор, принимающий описание, если хотите...
Ответ 4
Метод what
является виртуальным, и смысл в том, что вы должны переопределить его для возврата любого сообщения, которое хотите вернуть.
Ответ 5
Если ваша цель - создать исключение, чтобы вы не генерировали универсальное исключение (cpp: S112), вы можете просто захотеть предоставить исключение, от которого унаследовали (С++ 11), с помощью объявления using.
Вот минимальный пример для этого:
#include <exception>
#include <iostream>
struct myException : std::exception
{
using std::exception::exception;
};
int main(int, char*[])
{
try
{
throw myException{ "Something Happened" };
}
catch (myException &e)
{
std::cout << e.what() << std::endl;
}
return{ 0 };
}
Как указывает Килиан в разделе комментариев, пример зависит от конкретной реализации std :: exception, которая предлагает больше конструкторов, чем упомянуто здесь.
Во избежание этого вы можете использовать любой из удобных классов, предопределенных в заголовке <stdexcept>
. Посмотрите эти " Категории исключений " для вдохновения.