C++能否重复使用fstream来打开和写入多个文件?

25

我有10个文件需要按顺序写入。我是否可以只使用一个fstream完成这个任务?在每个文件之间,我需要做特殊的事情吗(除了flush())?还是只需要为每个文件调用open(file1, fstream::out | std::ofstream::app)并在所有10个文件都被写入后关闭流。

3个回答

31

你需要先关闭它,因为在已打开的流上调用open将失败。(这意味着failbit标志被设置为true)。注意close()会刷新,所以你不需要担心这个:

std::ofstream file("1");
// ...
file.close();
file.clear(); // clear flags
file.open("2");
// ...

// and so on

还要注意,最后一次不需要使用close();析构函数会替你完成这个操作(因此也会调用flush())。这可能会成为一个很好的实用函数:

template <typename Stream>
void reopen(Stream& pStream, const char * pFile,
            std::ios_base::openmode pMode = ios_base::out)
{
    pStream.close();
    pStream.clear();
    pStream.open(pFile, pMode);
}

然后你会得到:

std::ofstream file("1");
// ...
reopen(file, "2")
// ...

// and so on

5
最好在调用close()open()之间插入对clear()的调用,因为状态标志没有被清除。请参阅http://gcc.gnu.org/onlinedocs/libstdc++/faq.html#faq.stream_reopening_fails以获取详细说明。 - Danilo Piazzalunga
FILE变量有类似的东西吗?我的意思是多次重复使用。特别是用于写入。fclose()没有帮助。 - Alexandru Barbarosie
你能解释一下"1"和"2"吗? - undefined

2
是的,但是在使用相同的fstream打开下一个文件之前,您必须关闭它。
然而,更好的做法是为每个文件访问使用一个新的作用域fstream对象,以利用构造函数和析构函数的行为:
struct {
    const char *filename;
    void (*operation)(fstream&);
} filelist[] = {
    { "file1", callback1 },
    { "file2", callback2 },
    ...
    { "file10", callback10 },
};

for (int i = 0; i < 10; ++i) {
    fstream f(filelist[i].filename);
    filelist[i].operation(f);
}

在上面的代码示例中,每次通过for循环时都会刷新并关闭fstream,因为当对象失去作用域时调用了析构函数。 fstream被引用传递给回调函数,以便可以对每个文件进行单独处理操作,而不需要一个复杂的switch语句。如果每个文件的操作都相同,则可以消除该结构。

2
关闭流意味着执行flush(),只要在打开下一个流之前关闭每个流,就应该没问题。

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接