Click to See Complete Forum and Search --> : Inheriting from std::runtime_error or std::exception?


ltcmelo
February 14th, 2006, 09:03 AM
Hi!
I'm having a conceptual doubt about this issue.
I building a hierarchy of exceptions for my application. So, I need (not that I need, but I want) to inherit my base exception type from exception. This way, others can catch my exceptions in a catch(std::exception e) block. However, I don't know if I should inherit from runtime_error, which already inherits from exception.
The interesting thing is that exception doesn't have a constructor with const char*messge argument. And runtime_error does. BUT, exception actually has the virtual const char* what() {return->message;}. So, it's possible to inherit from exception (just do not make a constructor with this argument) and "hide" the virtal const char* what() method from exception.
So, can any expert help me out clarify this.
Thank you very much.


This compiles (comeau online).

#include <stdexcept>

class MyException : public std::runtime_error {
public:
MyException(const char* m) : std::runtime_error(m) { }
};


int main(int argc, char* argv[])
{
int a = 2;
if (a == 2)
{
throw MyException("teste");
}

return 0;
}

This fails (comeau online)

#include <stdexcept>

class MyException : public std::exception {
public:
MyException(const char* m) : std::exception(m) { }
};


int main(int argc, char* argv[])
{
int a = 2;
if (a == 2)
{
throw MyException("teste");
}

return 0;
}


This also compiles but i get warning (comeau online)

#include <stdexcept>

class GraphManipulationException : public std::exception
{
private:
const char* message;

public:
GraphManipulationException(){}
GraphManipulationException(const char* message):message(message){}

virtual int ha(){return 1;}
const char* what() { return this->message; }
};


int main(int argc, char* argv[])
{
throw GraphManipulationException("test");

return 0;
}

NMTop40
February 14th, 2006, 09:09 AM
Do you really need a big hierarchy of exceptions? Are you going to catch some but not others?

I used to do that but now I generally through std::invalid_argument most of the time and generally catch std::exception.

Anyway, to answer your actual question, std::exception is an abstract base class that has no class members so it doesn't have anyway to store your pointer. runtime_error is a concrete class so it must store it somewhere. It takes a const std::string & parameter and implicitly this can also be const char *.

exterminator
February 14th, 2006, 09:43 AM
It's better to inherit from std::exception for your business logic related exceptions.. as far as runtime_error is concerned ... i would not inherit from it unless there is something that really comes up and is identifiable at run time only. By the way, I did not understand what you meant by this:
The interesting thing is that exception doesn't have a constructor with const char*messge argument. And runtime_error does. BUT, exception actually has the virtual const char* what() {return->message;}. So, it's possible to inherit from exception (just do not make a constructor with this argument) and "hide" the virtal const char* what() method from exception.How would there be an hiding by providing a constructor? Regards.

ltcmelo
February 14th, 2006, 03:58 PM
Thanks for answers.
Exterminator, this is what I mean by the text. std::exception doesn't have a constructor with the 'const char* message' argument. However, it already has the what() method, which returns a 'message'. Got the point? So, if it has the what() method already, why couldn't it have the constructor with the message?

exterminator
February 15th, 2006, 02:50 AM
You do not need to worry about that.. When you derive from std::exception you can provide your own constructors to take in various arguments... for std::exception the value returned by what() has been left un-specified.

In the example that you have shown where you derive from std::exception, do not use the constructor for base that does not exist. In addition to that, over-ride the what() function to achieve what you want to. Regards.

treuss
February 15th, 2006, 03:18 AM
Thanks for answers.
Exterminator, this is what I mean by the text. std::exception doesn't have a constructor with the 'const char* message' argument. However, it already has the what() method, which returns a 'message'. Got the point? So, if it has the what() method already, why couldn't it have the constructor with the message?std::exception is an abstract base class. As such, it defines the interface of the derived classes to use, e.g. to provide a what() message that returns a const char*. However, std::exception does not provide the means of how the string returned by what() should be created, so a derived class could have it static, create it by taking an argument in the constructor, or create it dynamically when the what function is called.

exterminator
February 15th, 2006, 03:28 AM
std::exception is an abstract base class.It is not an abstract class. It is instantiable. It does not contain any pure virtual functions.