我正在使用Visual Studio 2012构建一个处理输入文件和输出文件的程序。
我这样实施:
ifstream inputFile;
ofstream outputFile;
inputFile.exceptions ( ifstream::failbit | ifstream::badbit );
try
{
// some codes here
inputFile.open(inputFileName.c_str());
cout << "Input file opened" << endl;
outputFile.open(outputFileName.c_str());
cout << "Output file opened" << endl;
}
catch (ifstream::failure e)
{
cerr << "Failed to open input file" << endl;
return -1;
}
catch (ofstream::failure e)
{
cerr << "Failed to open output file" << endl;
return -1;
}
发生编译错误:
error C2312: 'std::ios_base::failure' : is caught by 'std::ios_base::failure' at line 248
如何使用两个异常来源实现try-catch?
答案 0 :(得分:3)
您的问题是ifstream::failure
和ofstream::failure
属于同一类型(从ios_base继承到它们),
由于它是同一个异常,编译器会抱怨。
顺便说一句,你应该catch by const reference以避免不必要的副本。
答案 1 :(得分:0)
如您所见,抛出的异常类型是相同的。但是,由于你的检查是在文件开头附近完成的,你可以毫无例外地做到,不是吗?像:
#include <iostream>
#include <fstream>
#include <string>
using namespace std;
int main() {
string inputFileName { "/notexists" };
string outputFileName { "/notexistsandprobablynotwritable" };
ifstream inputFile { inputFileName };
if( !inputFile ) {
cerr << "Failed to open input file" << endl;
return -1;
}
cout << "Input file opened" << endl;
ofstream outputFile { outputFileName };
if( !outputFile ) {
cerr << "Failed to open output file" << endl;
return -1;
}
cout << "Output file opened" << endl;
}
或者,如果您确实需要例外,您可以在开放站点自己抛出不同的例外:
#include <iostream>
#include <fstream>
#include <string>
using namespace std;
template<typename Stream, typename Exception = typename Stream::failure>
void try_open(Stream& s, string filename) {
s.open(filename);
if( !s )
throw Exception( string("cannot open ")+filename );
}
struct input_exception: ifstream::failure { input_exception(const string& s): ifstream::failure(s) {} };
struct output_exception: ofstream::failure { output_exception(const string& s): ofstream::failure(s) {} };
int main() {
string inputFileName { "/notexists" };
string outputFileName { "/notexistsandprobablynotwritable" };
try {
ifstream inputFile;
try_open<ifstream, input_exception>(inputFile, inputFileName);
cout << "Input file opened" << endl;
ofstream outputFile;
try_open<ofstream, output_exception>(outputFile, outputFileName);
cout << "Output file opened" << endl;
} catch(const output_exception& e) {
cerr << "output exception!\n" << e.what() << "\n";
} catch(const input_exception& e) {
cerr << "input exception!\n" << e.what() << "\n";
} catch(const exception& e) {
cerr << "exception!\n" << e.what() << "\n";
}
}