473,320 Members | 1,940 Online
Bytes | Software Development & Data Engineering Community
Post Job

Home Posts Topics Members FAQ

Join Bytes to post your question to a community of 473,320 software developers and data experts.

exceptions

Hello. Here I am again trying to understand the examples of a C++
tutorial. When compiling the original source code:

// standard exceptions
#include <iostream>
#include <exception>
using namespace std;

class myexception: public exception
{
// virtual const char* what() const
char* what()
{
return "My exception happened";
}
} myex;

int main () {
try
{
throw myex;
}
catch (exception& e)
{
cout << e.what() << endl;
}
return 0;
}

I get this:

11myexception

which obviously is not the desired answer. I modified slightly the
code, just writing as type of the argument of the "catch" function the
derived class (myexception) , instead the "parent" one (exception) in
which case I am forced to declare the object function "what" as
public (reason for the difference with respect to the former case ???):
// standard exceptions
#include <iostream>
#include <exception>
using namespace std;

class myexception: public exception
{
// virtual const char* what() const

public:
char* what()
{
return "My exception happened";
}
} myex;

int main () {
try
{
throw myex;
}
catch (myexception& e)
{
cout << e.what() << endl;
}
return 0;
}

Now I get the right answer:

My exception happened

Can someone explain to me the reason of this. I would rather expect
that the type of the parent class could be used for the argument of the
calling function . Or not?

regards

Sep 21 '06 #1
10 3859
Josefo wrote:
Hello. Here I am again trying to understand the examples of a C++
tutorial. When compiling the original source code:

// standard exceptions
#include <iostream>
#include <exception>
using namespace std;

class myexception: public exception
{
// virtual const char* what() const
char* what()
This does not override the function in std::exception because you
changed the signature. Delete the line above and uncomment the line
above that, and then you need only to make it public (cf.
http://www.parashift.com/c++-faq-lit...html#faq-21.1).
{
return "My exception happened";
}
} myex;
Don't create an instance here. Create it where you throw.
>
int main () {
try
{
throw myex;
throw myexception();
}
catch (exception& e)
Prefer to catch by const reference:

catch (const exception& e)
{
cout << e.what() << endl;
}
return 0;
}

I get this:

11myexception

which obviously is not the desired answer. I modified slightly the
code, just writing as type of the argument of the "catch" function the
derived class (myexception) , instead the "parent" one (exception) in
which case I am forced to declare the object function "what" as
public (reason for the difference with respect to the former case ???):
// standard exceptions
#include <iostream>
#include <exception>
using namespace std;

class myexception: public exception
{
// virtual const char* what() const

public:
char* what()
{
return "My exception happened";
}
} myex;

int main () {
try
{
throw myex;
}
catch (myexception& e)
{
cout << e.what() << endl;
}
return 0;
}

Now I get the right answer:

My exception happened

Can someone explain to me the reason of this. I would rather expect
that the type of the parent class could be used for the argument of the
calling function . Or not?
You can (and often should) use the parent class to catch. Just fix your
exception class as I describe above.

Cheers! --M

Sep 21 '06 #2
mlimber wrote:
Josefo wrote:
Hello. Here I am again trying to understand the examples of a C++
tutorial. When compiling the original source code:

// standard exceptions
#include <iostream>
#include <exception>
using namespace std;

class myexception: public exception
{
// virtual const char* what() const
char* what()

This does not override the function in std::exception because you
changed the signature.
Hello. Can you explain me what do you mean by "changing signature"?.
>Delete the line above and uncomment the line
above that, and then you need only to make it public (cf.
http://www.parashift.com/c++-faq-lit...html#faq-21.1).
. I did it. It does not yet work. I should eliminate the last "const"
in the line to be uncommented (on the other hand it has no meaning and
should be an error, am I right?).
About the need to make it public: there is a public inheritance from
exception to myexception, therefore all public members of the base
class should be also public for the derived one, right? So, why should
I declare as public the "what" member function which supposedly is
public (or not?) in the base class?.
{
return "My exception happened";
}

} myex;

Don't create an instance here. Create it where you throw.

int main () {
try
{
throw myex;

throw myexception();
}
catch (exception& e)

Prefer to catch by const reference:

catch (const exception& e)
{
cout << e.what() << endl;
}
return 0;
}
>
You can (and often should) use the parent class to catch. Just fix your
exception class as I describe above.

Cheers! --M
I tried to do as uou suggest, but with no results. By the way, as far
as I know (very little, evidently..) the "virtual" word should only be
used when the declaration of the virtual function is made in the base
class, not when defined in a derived class declaration. right? In fact,
when I leave it it makes no difference (apparently, at least), it gives
no error at compilation but the result is the same ( the output is:
11myexception)

Here is the code:

// standard exceptions
#include <iostream>
#include <exception>
using namespace std;

class myexception: public exception
{
// virtual const char* what() const
public:
const char* what()

// char* what()
{
return "My exception happened";
}
//} myex;
};

int main () {
try
{
// throw myex;
throw myexception();

}
// catch (exception& e)
catch (const exception& e)
{
cout << e.what() << endl;
}
return 0;
}

Cheers
Josefo

Sep 22 '06 #3
Josefo wrote:
mlimber wrote:
Josefo wrote:
Hello. Here I am again trying to understand the examples of a C++
tutorial. When compiling the original source code:
>
// standard exceptions
#include <iostream>
#include <exception>
using namespace std;
>
class myexception: public exception
{
// virtual const char* what() const
char* what()
This does not override the function in std::exception because you
changed the signature.

Hello. Can you explain me what do you mean by "changing signature"?.
The signature of the what function in std::exception is:

virtual const char* what() const

but the signature of your function is different:

char* what()

Virtual is optional in your override, but the consts are not.
Delete the line above and uncomment the line
above that, and then you need only to make it public (cf.
http://www.parashift.com/c++-faq-lit...html#faq-21.1).

. I did it. It does not yet work.
User error, methinks. This code works for me:

#include <iostream>
#include <exception>
using namespace std;

class myexception : public exception
{
public:
virtual const char* what() const
{
return "My exception happened";
}
};

int main()
{
try
{
throw myexception();
}
catch( const exception& e )
{
cout << e.what() << endl;
}
return 0;
}
I should eliminate the last "const"
in the line to be uncommented (on the other hand it has no meaning and
should be an error, am I right?).
No. See
<http://www.parashift.com/c++-faq-lite/const-correctness.html#faq-18.10>.
About the need to make it public: there is a public inheritance from
exception to myexception, therefore all public members of the base
class should be also public for the derived one, right? So, why should
I declare as public the "what" member function which supposedly is
public (or not?) in the base class?.
Because you are *changing* its access. This is permissible but evil.
See
<http://www.parashift.com/c++-faq-lite/proper-inheritance.html#faq-21.1>.
{
return "My exception happened";
}
} myex;
Don't create an instance here. Create it where you throw.
>
int main () {
try
{
throw myex;
throw myexception();
}
catch (exception& e)
Prefer to catch by const reference:

catch (const exception& e)
{
cout << e.what() << endl;
}
return 0;
}

You can (and often should) use the parent class to catch. Just fix your
exception class as I describe above.

Cheers! --M

I tried to do as uou suggest, but with no results. By the way, as far
as I know (very little, evidently..) the "virtual" word should only be
used when the declaration of the virtual function is made in the base
class, not when defined in a derived class declaration. right? In fact,
when I leave it it makes no difference (apparently, at least), it gives
no error at compilation but the result is the same ( the output is:
11myexception)
The virtual keyword is optional. Personally, I prefer to put it in
derived classes to remind me that the function in question is
overriding a function from a base class.
Here is the code:

// standard exceptions
#include <iostream>
#include <exception>
using namespace std;

class myexception: public exception
{
// virtual const char* what() const
public:
const char* what()
Without making this a const member function (that's what the const at
the end does), you have unintentionally created a const overload (see
<http://www.parashift.com/c++-faq-lite/const-correctness.html#faq-18.12>)
that does not replace std::exception::what().

It's like if you did this:

struct Base
{
virtual void f( int ) { /*...*/ }
};

struct Derived : Base
{
virtual void f( double ) { /*...*/ }
};

Derived has not actually override f(int) because you changed the
function signature. So...

void Foo( Base& pb, Derived& pd )
{
pb.f( 1 ); // ok: calls Base::f(int)
pd.f( 1 ); // ok: calls Base::f(int)

pb.f( 1.1 ); // compile-time error!
pd.f( 1.1 ); // ok: calls Derived::f(double)
}

Cheers! --M

Sep 22 '06 #4
Hello:
mlimber wrote:
>This code works for me:

#include <iostream>
#include <exception>
using namespace std;

class myexception : public exception
{
public:
virtual const char* what() const
{
return "My exception happened";
}
};

int main()
{
try
{
throw myexception();
}
catch( const exception& e )
{
cout << e.what() << endl;
}
return 0;
}
But not for me. I get this run-time errors:

josemanuel@josefo:~/C++/C++_Language_Tutorial$ c++
standard_exception_mlimber_good.c
standard_exception_mlimber_good.c:8: error: especificador throw más
flexible para 'virtual const char* myexception::what() const'
/usr/lib/gcc/i486-linux-gnu/4.0.3/../../../../include/c++/4.0.3/exception:61:
error: sustituyendo 'virtual const char* std::exception::what()
const throw ()'
(By the way, trivial spanish-to-english translation:
especificador mas flexible para ...............more flexible specifier
for
substituyendo..................................sub stituting
)
I am running this versionof the compiler:

josemanuel@josefo:~/C++/C++_Language_Tutorial$ c++ -v
Usando especificaciones internas.
Objetivo: i486-linux-gnu
Configurado con: ../src/configure -v
--enable-languages=c,c++,java,f95,objc,ada,treelang --prefix=/usr
--enable-shared --with-system-zlib --libexecdir=/usr/lib
--without-included-gettext --enable-threads=posix --enable-nls
--program-suffix=-4.0 --enable-__cxa_atexit --enable-clocale=gnu
--enable-libstdcxx-debug --enable-java-awt=gtk-default
--enable-gtk-cairo
--with-java-home=/usr/lib/jvm/java-1.4.2-gcj-4.0-1.4.2.0/jre
--enable-mpfr --disable-werror --with-tune=pentium4
--enable-checking=release i486-linux-gnu
Modelo de hilos: posix
gcc versión 4.0.3 (Ubuntu 4.0.3-1ubuntu5)
(translation:
usando especificaciones internas.......using internal specifications
Configurando...configuring
modelo de hilos....model of threads)

Some hint? Cheers

Josefo

Sep 22 '06 #5
Josefo wrote:
Hello:
mlimber wrote:
This code works for me:

#include <iostream>
#include <exception>
using namespace std;

class myexception : public exception
{
public:
virtual const char* what() const
{
return "My exception happened";
}
};

int main()
{
try
{
throw myexception();
}
catch( const exception& e )
{
cout << e.what() << endl;
}
return 0;
}

But not for me. I get this run-time errors:

josemanuel@josefo:~/C++/C++_Language_Tutorial$ c++
standard_exception_mlimber_good.c
standard_exception_mlimber_good.c:8: error: especificador throw más
flexible para 'virtual const char* myexception::what() const'
/usr/lib/gcc/i486-linux-gnu/4.0.3/../../../../include/c++/4.0.3/exception:61:
error: sustituyendo 'virtual const char* std::exception::what()
const throw ()'
(By the way, trivial spanish-to-english translation:
especificador mas flexible para ...............more flexible specifier
for
substituyendo..................................sub stituting
)
I am running this versionof the compiler:

josemanuel@josefo:~/C++/C++_Language_Tutorial$ c++ -v
Usando especificaciones internas.
Objetivo: i486-linux-gnu
Configurado con: ../src/configure -v
--enable-languages=c,c++,java,f95,objc,ada,treelang --prefix=/usr
--enable-shared --with-system-zlib --libexecdir=/usr/lib
--without-included-gettext --enable-threads=posix --enable-nls
--program-suffix=-4.0 --enable-__cxa_atexit --enable-clocale=gnu
--enable-libstdcxx-debug --enable-java-awt=gtk-default
--enable-gtk-cairo
--with-java-home=/usr/lib/jvm/java-1.4.2-gcj-4.0-1.4.2.0/jre
--enable-mpfr --disable-werror --with-tune=pentium4
--enable-checking=release i486-linux-gnu
Modelo de hilos: posix
gcc versión 4.0.3 (Ubuntu 4.0.3-1ubuntu5)
(translation:
usando especificaciones internas.......using internal specifications
Configurando...configuring
modelo de hilos....model of threads)

Some hint? Cheers
Looks like your std::exception::what() has a no-throw specification.
Make your overload read:

virtual const char* what() const throw()
{ ... }

Cheers! --M

Sep 22 '06 #6
mlimber wrote:
Looks like your std::exception::what() has a no-throw specification.
Make your overload read:

virtual const char* what() const throw()
{ ... }

Cheers! --M
Thanks, you are right. And finally...how may I override the no- throw
specification when the exception is launched directly? (without the
"throw myexception", which prevents me to override the no-throw
specification when declaring the derived class "myexception"). For
instance:

// bad_alloc standard exception
#include <iostream>
#include <exception>
using namespace std;

int main () {
try
{
int* myarray= new int[1000000000];
}
catch (exception& e)
{
cout << "Standard exception: " << e.what() << endl;
}
return 0;
}

I get ( thanks to you, now I undestand why, but I do not know how to
solve it):

josemanuel@josefo:~/C++/C++_Language_Tutorial$ ./a.out
Standard exception: St9bad_alloc
Cheers

Josefo

Sep 22 '06 #7
Josefo wrote:
mlimber wrote:
Looks like your std::exception::what() has a no-throw specification.
Make your overload read:

virtual const char* what() const throw()
{ ... }

Cheers! --M

Thanks, you are right. And finally...how may I override the no- throw
specification when the exception is launched directly? (without the
"throw myexception", which prevents me to override the no-throw
specification when declaring the derived class "myexception"). For
instance:
I think you mean "indirectly" since in the example below "new"
generates the exception ("directly" would be an explicit throw
statement on your part as in the previous posts).
// bad_alloc standard exception
#include <iostream>
#include <exception>
using namespace std;

int main () {
try
{
int* myarray= new int[1000000000];
}
catch (exception& e)
{
cout << "Standard exception: " << e.what() << endl;
}
return 0;
}

I get ( thanks to you, now I undestand why, but I do not know how to
solve it):

josemanuel@josefo:~/C++/C++_Language_Tutorial$ ./a.out
Standard exception: St9bad_alloc
I don't understand what the problem is. You get a std::bad_alloc
exception, which is just what you should get if new fails. What were
you expecting?

Cheers! --M

Sep 22 '06 #8
Josefo wrote:
mlimber wrote:
>Looks like your std::exception::what() has a no-throw specification.
Make your overload read:

virtual const char* what() const throw()
{ ... }

Cheers! --M

Thanks, you are right. And finally...how may I override the no- throw
specification when the exception is launched directly? (without the
"throw myexception", which prevents me to override the no-throw
specification when declaring the derived class "myexception"). For
instance:
I think you're confused. the no throw specification means that what()
is guaranteed not to throw.

Sep 23 '06 #9
In article <jY***************@newssvr11.news.prodigy.com>,
no*****@here.dude says...

[ ... ]
I think you're confused. the no throw specification means that what()
is guaranteed not to throw.
Not really. It really means if it throws anything, unexpected() will be
called (and by default, unexpected() will call terminate()). Therefore,
what() can throw, but nothing can catch whatever it throws. The user can
use set_unexpected to change the default behavior, but the unexpected
handler cannot return -- it can only exit by throwing another exception
that is allowed by the original exception specification. Since that list
is empty in this case, you can't do a whole lot else in the unexpected
exception handler either...

--
Later,
Jerry.

The universe is a figment of its own imagination.
Sep 23 '06 #10
mlimber wrote:
>
I think you mean "indirectly" since in the example below "new"
generates the exception ("directly" would be an explicit throw
statement on your part as in the previous posts).
You are right. I'm sorry, I was messing the things.
>
// bad_alloc standard exception
#include <iostream>
#include <exception>
using namespace std;

int main () {
try
{
int* myarray= new int[1000000000];
}
catch (exception& e)
{
cout << "Standard exception: " << e.what() << endl;
}
return 0;
}

I get ( thanks to you, now I undestand why, but I do not know how to
solve it):

josemanuel@josefo:~/C++/C++_Language_Tutorial$ ./a.out
Standard exception: St9bad_alloc

I don't understand what the problem is. You get a std::bad_alloc
exception, which is just what you should get if new fails. What were
you expecting?
Right. Thanks a lot to all of you.

Cheers.

Josefo

Sep 23 '06 #11

This thread has been closed and replies have been disabled. Please start a new discussion.

Similar topics

16
by: David Turner | last post by:
Hi all I noticed something interesting while testing some RAII concepts ported from C++ in Python. I haven't managed to find any information about it on the web, hence this post. The problem...
21
by: dkcpub | last post by:
I'm very new to Python, but I couldn't find anything in the docs or faq about this. And I fished around in the IDLE menus but didn't see anything. Is there a tool that can determine all the...
26
by: OvErboRed | last post by:
I just read a whole bunch of threads on microsoft.public.dotnet.* regarding checked exceptions (the longest-running of which seems to be <cJQQ9.4419 $j94.834878@news02.tsnz.net>. My personal...
9
by: Gianni Mariani | last post by:
I'm involved in a new project and a new member on the team has voiced a strong opinion that we should utilize exceptions. The other members on the team indicate that they have either been burned...
6
by: RepStat | last post by:
I've read that it is best not to use exceptions willy-nilly for stupid purposes as they can be a major performance hit if they are thrown. But is it a performance hit to use a try..catch..finally...
14
by: dcassar | last post by:
I have had a lively discussion with some coworkers and decided to get some general feedback on an issue that I could find very little guidance on. Why is it considered bad practice to define a...
8
by: cat | last post by:
I had a long and heated discussion with other developers on my team on when it makes sense to throw an exception and when to use an alternate solution. The .NET documentation recommends that an...
1
by: Anonieko | last post by:
Understanding and Using Exceptions (this is a really long post...only read it if you (a) don't know what try/catch is OR (b) actually write catch(Exception ex) or catch{ }) The first thing I...
2
by: Zytan | last post by:
I know that WebRequest.GetResponse can throw WebException from internet tutorials. However in the MSDN docs: http://msdn2.microsoft.com/en-us/library/system.net.webrequest.getresponse.aspx It...
0
RedSon
by: RedSon | last post by:
Chapter 3: What are the most common Exceptions and what do they mean? As we saw in the last chapter, there isn't only the standard Exception, but you also get special exceptions like...
0
isladogs
by: isladogs | last post by:
The next Access Europe meeting will be on Wednesday 6 Mar 2024 starting at 18:00 UK time (6PM UTC) and finishing at about 19:15 (7.15PM). In this month's session, we are pleased to welcome back...
1
isladogs
by: isladogs | last post by:
The next Access Europe meeting will be on Wednesday 6 Mar 2024 starting at 18:00 UK time (6PM UTC) and finishing at about 19:15 (7.15PM). In this month's session, we are pleased to welcome back...
0
by: Vimpel783 | last post by:
Hello! Guys, I found this code on the Internet, but I need to modify it a little. It works well, the problem is this: Data is sent from only one cell, in this case B5, but it is necessary that data...
0
by: jfyes | last post by:
As a hardware engineer, after seeing that CEIWEI recently released a new tool for Modbus RTU Over TCP/UDP filtering and monitoring, I actively went to its official website to take a look. It turned...
0
by: ArrayDB | last post by:
The error message I've encountered is; ERROR:root:Error generating model response: exception: access violation writing 0x0000000000005140, which seems to be indicative of an access violation...
0
by: CloudSolutions | last post by:
Introduction: For many beginners and individual users, requiring a credit card and email registration may pose a barrier when starting to use cloud servers. However, some cloud server providers now...
1
by: Shćllîpôpď 09 | last post by:
If u are using a keypad phone, how do u turn on JavaScript, to access features like WhatsApp, Facebook, Instagram....
0
by: af34tf | last post by:
Hi Guys, I have a domain whose name is BytesLimited.com, and I want to sell it. Does anyone know about platforms that allow me to list my domain in auction for free. Thank you
0
isladogs
by: isladogs | last post by:
The next Access Europe User Group meeting will be on Wednesday 3 Apr 2024 starting at 18:00 UK time (6PM UTC+1) and finishing by 19:30 (7.30PM). In this session, we are pleased to welcome former...

By using Bytes.com and it's services, you agree to our Privacy Policy and Terms of Use.

To disable or enable advertisements and analytics tracking please visit the manage ads & tracking page.