With this code:
int main()
{
try
{
throw -1;
}
catch (int& x)
{
std::cerr << "We caught an int exception with value: " << x << std::endl;
}
std::cout << "Continuing on our merry way." << std::endl;
return 0;
}
We have:
/tmp$ ./prorgam.out
Continuing on our merry way
We caught an int exception with value: -1
How does the catch
block read -1
as int&
? We couldn't assign a value to a non-const lvalue reference.
And why is the second std::cout
statement executed before the first std::cerr
statement?
This is okay because of [except.throw]/3
Throwing an exception copy-initializes ([dcl.init], [class.copy.ctor]) a temporary object, called the exception object. An lvalue denoting the temporary is used to initialize the variable declared in the matching handler ([except.handle]).
emphasis mine
As you can see, even though it is a temporary, the compiler treats it as an lvalue for initializing the handler. Because of this, you don't need a const reference.
From this throw
reference:
Unlike other temporary objects, the exception object is considered to be an lvalue argument when initializing the catch clause parameters, so it can be caught by lvalue reference, modified, and rethrown.
So while the "object" is temporary, it's still an lvalue and as such you can catch it by reference.
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With