Exceptions

Pages: 12
Apr 27, 2011 at 9:33pm
Is there a base class for exceptions? If so, what is it's name? (or, more importantly, it's header's name)

Also, can a new exception be defined in a Header (or *.cpp) file? If so, how?
Apr 27, 2011 at 9:39pm
Yes, there is:
http://www.cplusplus.com/reference/std/exception/exception/

Also, can a new exception be defined in a Header (or *.cpp) file? If so, how?

The same way as you would define any other class.
Apr 27, 2011 at 10:23pm
Is it better to inherit from std::exception, or std::runtime_exception, since surely most user defined exceptions are runtime exceptions?
Apr 27, 2011 at 10:33pm
Inherit from the most specialized case that you can.
Apr 27, 2011 at 10:45pm
Thanks!

But what does
1
2
3
4
5
6
7
8
class exception {
public:
  exception () throw();                             //?????
  exception (const exception&) throw();             //?????
  exception& operator= (const exception&) throw();  //?????
  virtual ~exception() throw();                     //?????
  virtual const char* what() const throw();         //?????
};

mean?
(It doesn't use many C++ features I know of)
Apr 27, 2011 at 11:21pm
The feature is called "classes".
Apr 28, 2011 at 12:13am
closed account (3hM2Nwbp)
What you're seeing in that class by line is:

1) class declaration
2) access specifier
3) constructor
4) copy constructor
5) assignment operator
6) destructor
7) member-method

Notice each method has throw() after it - this signifies that each of those calls will never throw an exception, no matter what.
Apr 28, 2011 at 1:09am
I know what classes are.
1
2
3
4
5
6
7
8
class classname {
    public:
        //declarations
    protected:
        //declarations
    private:
        //declarations
};


But I still don't understand these:
1
2
3
4
5
exception () throw();
exception (const exception&) throw();
exception& operator= (const exception&) throw();
virtual ~exception() throw();
virtual const char* what() const throw();

1
2
3
4
5
6
int main() {
    while(true) {
        std::cout << "Explain!\n";
    };
    return 0;
}

For the general syntax please, not just this specific case.
Apr 28, 2011 at 7:11am
I have written some basic explanations, but perhaps you would be better off reading the tutorials on this site, starting with this one: http://cplusplus.com/doc/tutorial/classes/

The first two are constructors:
1
2
3
4
5
6
class MyClass {
public:
   MyClass();
   MyClass(const MyClass&);
   // ...
};

These are constructors. They are called when an object of the class is created.
The first is a default constructor, with no arguments. This constructor is provided by default if no custom constructors are provided. The second is a copy constructor to define how one object of this type is copied to another. This, too, is usually provided by default.

The throw() means that the function does not throw any exception.
On the other hand, throw(some_type) means that the function would only throw an exception of type some_type. However, Visual C++ 2010 ignores the second one.

The third line
exception& operator= (const exception&) throw();
Is an assignment operator. It is a function to define how one object of this type is assigned to another of this type, using the assignment operator '='. It accepts a reference parameter of the same type as the class, which is the object on the other side of the equals sign. It returns a reference, which is the object assigned to.

For example:
1
2
   exception a();
   exception b = a;
The second line calls operator= with a reference to a as the argument. It returns the value of b after assignment.

Next is the destructor, ~exception. In general, these have the form ~class_name(). Note the lack of an argument list. This object is called when the lifetime of an object of this type ends. The virtual keyword is so that in derived classes, an override function with the same prototype in the derived class is called not the base one.

Virtual means the same in the last line. It is a member function called what which accepts no arguments, will not throw an exception and returns a pointer to a constant character array.

Hope this helps. See the tutorials on this site for details.
Apr 30, 2011 at 11:58am
Sorry to keep you waiting, I keep getting "Access Denied" on my posts.

I know what constructors are.
I just don't understand the throw()
Is it available for all functions, only class methods, or only Constructors and Destructors?
Can it be done for functions other than throw()?

Also, I did some research.
Is this valid code?
1
2
3
4
5
6
7
8
9
10
11
12
13
#include <exception>

class node_not_found : public std::exception {
    virtual const char* what() const throw() {
        return "Error: rhs is not contained in the path's current directory;"
    };
};

class path_full : public std::exception {
    virtual const char* what() const throw() {
        return "Error: This path is complete, therefore no new nodes may be added to it;"
    };
};

Apr 30, 2011 at 3:06pm
It looks fine to me. Was there any particular aspect you were unsure of?
Apr 30, 2011 at 4:21pm
No. I just wanted to make sure I understood the syntax.

By the way, what exactly does throw() do?

(and would I put throw(path_full) throw(node_not_found) after an operator declaration to indicate that it might return those exceptions?)
Apr 30, 2011 at 6:51pm
would I put throw(path_full) throw(node_not_found)

The correct syntax for this is
throw (path_full, node_not_found)

As for what exactly throw() does, it seems to be rather complex. This article I found discusses the feature. Indeed it also recommends against use of exception specification in most (almost all!) circumstances.

http://www.gotw.ca/publications/mill22.htm
Apr 30, 2011 at 7:18pm
Xander314 +1

Don't use throw() specifications. They are a mistake and, frankly, they are not always enforcible.

An exception class will naturally have a "no throw" specification, because exceptions should not be throwing exceptions -- that would complicate things significantly.
Apr 30, 2011 at 7:25pm
The article suggests that (at least in some versions), using throw () is fine in MSVC, since it does a better job of handling them. (I think it said that it doesn't enforce them, but instead trusts you and performs optimisations on the assumption that the function won't throw). Does that mean it's alright to use them in MSVC, at the cost of portability, of course?
Apr 30, 2011 at 7:35pm
If i inherit from std::exception, do i need to add throw()? Like:
1
2
3
4
5
6
7
class FooException : public std::exception
{
public:
    FooException() throw();//<--do i need this since its base class has it?
    const char* what() const throw();
    void SomeOtherMethod() throw();
};
Last edited on Apr 30, 2011 at 7:36pm
Apr 30, 2011 at 7:41pm
@Xander314
There is no portability cost. Throw specifications are part of the language.

@savavampir
It can't hurt.
Apr 30, 2011 at 7:49pm
Thanks. And last question, what to throw to catch default exception (not sure how it is called):
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
void foo()
{
    throw ???;
}

int main()
{
    try{
    foo();
    }
    catch(FooException& fe)
    {
         ...
    }
    catch(BarException& be)
    {
         ...
    }
   catch(otherExc& oe)
   {
    }
    catch(...)//THIS ONE
    {
        std::cout << "Default exception!!!";
    }
}
Last edited on Apr 30, 2011 at 7:53pm
Apr 30, 2011 at 7:51pm
@Xander314
There is no portability cost. Throw specifications are part of the language.

I know they are part of the specification. When I said portability loss I meant that while MSVC might handle throw() in a good way, not all compilers will. Thus code with ES which is happily optimised in MSVC might cause all the problems that article mentions with another compiler.

Don't use throw() specifications
It can't hurt.

I'm confused... are you saying that it's alright to use ES for exceptions, but nowhere else?
Last edited on Apr 30, 2011 at 7:52pm
Apr 30, 2011 at 8:15pm
@Savavampir
Throw an integer or anything that won't be specifically indicated. However, you shouldn't be doing that...

@Xander314
Pretty much.

Here's some reading for you

A Pragmatic Look at Exception Specifications by Herb Sutter
http://www.gotw.ca/publications/mill22.htm

Hope this helps.
Pages: 12