为什么捕获异常指针时异常不一样?
Why exception not the same when catching exception pointer?
我是 C++ 异常处理的新手。我试图抛出一个异常指针并捕获了它,但似乎后来捕获的异常与我抛出的异常不同。
这是我的代码:
try {
bad_exception e2 = bad_exception();
cout << e2.what() << endl;
cout << &e2 << endl;
throw &e2;
}
catch (bad_exception* ex) {
cout << ex << endl;
cout << ex->what() << endl;
cout << (*ex).what() << endl;
}
输出:
错误异常
00CFFCF8
00CFFCF8
未知异常
未知异常
我预计后者会显示同名的“错误异常”。你能解释一下吗?
更新:
似乎异常具有“自动删除”功能?我尝试抛出一个指向普通对象的指针(不是从异常继承的)。但是我仍然可以在 catch 块中访问该对象及其属性。
try {
char str[5] = "eed8";
A a = A();
a.name1 = str;
cout << a.show() << endl;
cout << &a << endl;
throw &a;
}
catch (A* exp) {
cout << exp << endl;
cout << exp->show() << endl;
cout << exp->name1 << endl;
}
输出:
eed8
007BF9DC
007BF9DC
eed8
eed8
您应该(通常)按值抛出异常。
这里的问题是您正在抛出一个指向对象的指针。不幸的是,当指针被捕获时,它指向的对象已经被销毁,因此你有一个无效的指针。
try {
bad_exception e2 = bad_exception();
cout << e2.what() << endl;
cout << &e2 << endl;
throw &e2;
} // At this point the object "e2" goes out of scope
// Thus its destructor is called.
// So the pointer you threw now points at an invlalid object
// Thus accessign the object via this pointer is UB.
catch (bad_exception* ex) {
cout << ex << endl;
cout << ex->what() << endl;
cout << (*ex).what() << endl;
}
改写成这样:
try {
bad_exception e2 = bad_exception();
cout << e2.what() << endl;
cout << &e2 << endl;
throw e2; // Throw a copy.
// Throw an object that gets copied to a secure location
// so that when you catch it is still valid.
}
catch (bad_exception const& ex) { // catch and get a reference to the copy.
cout << &ex << endl;
cout << ex.what() << endl;
}
如果你绝对必须抛出一个指针,那么使用 new
来确保指针有一个动态的生命周期(但记住,你需要清理它)。
更新:
It seems the exception has the "auto delete" feature?
不是东西。
I tried throwing a pointer to normal object (not inherited from exception).
异常对象(或其任何派生的 classes)没有什么特别之处。它只是一个普通的对象。像所有对象(class)一样,对象的析构函数是 运行 当对象到达其生命周期结束时。如果 A
没有析构函数,那么对象使用的内存可能不会改变(但它不能被不是你的对象的其他对象使用)。
But I can still access the object and its properties in the catch block.
这就是“未定义行为”不好的一面。我可能看起来它正在工作。它不起作用,它只是看起来像它。在其他情况下也可能不起作用。
我是 C++ 异常处理的新手。我试图抛出一个异常指针并捕获了它,但似乎后来捕获的异常与我抛出的异常不同。 这是我的代码:
try {
bad_exception e2 = bad_exception();
cout << e2.what() << endl;
cout << &e2 << endl;
throw &e2;
}
catch (bad_exception* ex) {
cout << ex << endl;
cout << ex->what() << endl;
cout << (*ex).what() << endl;
}
输出:
错误异常
00CFFCF8
00CFFCF8
未知异常
未知异常
我预计后者会显示同名的“错误异常”。你能解释一下吗?
更新:
似乎异常具有“自动删除”功能?我尝试抛出一个指向普通对象的指针(不是从异常继承的)。但是我仍然可以在 catch 块中访问该对象及其属性。
try {
char str[5] = "eed8";
A a = A();
a.name1 = str;
cout << a.show() << endl;
cout << &a << endl;
throw &a;
}
catch (A* exp) {
cout << exp << endl;
cout << exp->show() << endl;
cout << exp->name1 << endl;
}
输出:
eed8
007BF9DC
007BF9DC
eed8
eed8
您应该(通常)按值抛出异常。
这里的问题是您正在抛出一个指向对象的指针。不幸的是,当指针被捕获时,它指向的对象已经被销毁,因此你有一个无效的指针。
try {
bad_exception e2 = bad_exception();
cout << e2.what() << endl;
cout << &e2 << endl;
throw &e2;
} // At this point the object "e2" goes out of scope
// Thus its destructor is called.
// So the pointer you threw now points at an invlalid object
// Thus accessign the object via this pointer is UB.
catch (bad_exception* ex) {
cout << ex << endl;
cout << ex->what() << endl;
cout << (*ex).what() << endl;
}
改写成这样:
try {
bad_exception e2 = bad_exception();
cout << e2.what() << endl;
cout << &e2 << endl;
throw e2; // Throw a copy.
// Throw an object that gets copied to a secure location
// so that when you catch it is still valid.
}
catch (bad_exception const& ex) { // catch and get a reference to the copy.
cout << &ex << endl;
cout << ex.what() << endl;
}
如果你绝对必须抛出一个指针,那么使用 new
来确保指针有一个动态的生命周期(但记住,你需要清理它)。
更新:
It seems the exception has the "auto delete" feature?
不是东西。
I tried throwing a pointer to normal object (not inherited from exception).
异常对象(或其任何派生的 classes)没有什么特别之处。它只是一个普通的对象。像所有对象(class)一样,对象的析构函数是 运行 当对象到达其生命周期结束时。如果 A
没有析构函数,那么对象使用的内存可能不会改变(但它不能被不是你的对象的其他对象使用)。
But I can still access the object and its properties in the catch block.
这就是“未定义行为”不好的一面。我可能看起来它正在工作。它不起作用,它只是看起来像它。在其他情况下也可能不起作用。