一些高層次的代碼一般會正好趕上std::exception
並打印what()
。您希望儘可能多地向這個通用機制提供信息,但不會丟失任何信息。考慮一些歸檔庫的實現:
archive::archive(const char* filename)
{
ifstream file(filename)
file.exceptions(ios_base::badbit);
open_archive(file); // throws ios_base::failure, or some other low-level exception.
}
檔案可用的信息沒有被記錄(例如文件名)。此外,您還想區分來自存檔類的異常和其他異常。
archive::archive(const char* filename)
{
try {
ifstream file(filename)
file.exceptions(ios_base::badbit);
open_archive(file); // throws ios_base::failure, or some other low-level exception.
} catch(const std::exception& e) {
throw archive_exception("Can't open archive", filename, e.what());
}
}
現在我們增加了更高級別的語義信息archive
類知道,但我們也失去了對問題的最初原因(的e
類型)的信息。 nested_exception
是爲了解決這個問題:
archive::archive(const char* filename)
{
try {
ifstream file(filename)
file.exceptions(ios_base::badbit);
open_archive(file); // throws ios_base::failure, or some other low-level exception.
} catch(...) {
throw_with_nested(archive_exception("Can't open archive", filename));
}
}
所有可用的信息被記錄。我們現在可以在捕獲網站中一般檢索它:
void print_exception_info(const std::exception& e)
{
cerr << e.what() << "\n";
try {
rethrow_if_nested(e);
} catch(const std::exception& ne) {
print_exception_info(ne);
} catch(...) { }
}
int main() {
try {
run();
} catch(const std::exception& e) {
print_exception_info(e);
}
}
輸出將比以前更具描述性。它將描述從高層開始低級的問題:
無法打開檔案「my_archive.bin」
訪問被拒絕。
或許:
無法打開檔案 「my_archive.bin」
實錄 'AABB' 未找到。
與exception_ptr
一起使用的功能旨在傳遞線程之間的異常,或者更一般地說,存儲異常以供以後使用。它們的工作方式取決於實施。目的是exception_ptr
將是一個共享指針異常對象。但是,當創建這個指針時,拋出異常或試圖獲得一個exception_ptr
時,將受到實現的約束。當您致電current_exception()
時,實施仍可以自由複製異常。
該標準提供了一個很好的(最好的?)描述。您可以免費閱讀最後一個[公開可用草稿](http://www.open-std.org/jtc1/sc22/wg21/docs/papers/2011/n3242.pdf)。 – ybungalobill