指针访问std :: fstream时出现问题

时间:2014-05-20 23:20:15

标签: c++ io c++98

很长一段时间没有使用C ++的i / o工具(而是使用C linux API操作),我试图至少熟悉C ++正确做事的方式。我在Ubuntu 12.04下工作,根据C ++ 98,使用gcc -Wall编译没有错误或警告。当我需要创建一个我将首先写入的新文件,然后再读取时,问题出现了。问题如下:

#include <fstream>

std::fstream::openmode o_M = std::fstream::in | std::fstream::out;
std::fstream::openmode o_M1 = o_M | std::fstream::trunc;

std::fstream* preproc;
preproc = new std::fstream(out_Name.c_str(), o_M1); // (1)
if ( !(preproc->good()) )
    errExit(1, "can't open file <%s>", out_Name.c_str());

preproc->put('c');
(*preproc) << "foo";  

据我所知,这应该将“cfoo”写入文件;但是,没有任何内容写入,而文件是使用适当的权限创建的。我已经经历了许多可能是错误的迭代(清除流;以不同模式打开;明确地首先打开指向文件; ...),但无济于事。此外,在同一个项目的早期,我创建并使用指向现有文件的fstream指针没问题(使用相同的语法,没有openmode限定符(我当然也试过不对文件使用openmodes)上面)) - 仅从现有文件中读取。

当我改为使用非指针访问时,如

std::fstream TEST(out_Name.c_str(), o_M1); // (etc, ancillary changes)

一切正常。

我很困惑。我可能没有看到森林里的树木,如果有人指出我错过了什么,我将不胜感激。

1 个答案:

答案 0 :(得分:5)

您不是flushclosedelete流,因此缓冲区不会被刷新。您的堆栈版本有效,因为当对象在超出范围后被销毁时,流被刷新并关闭。

刷新流,例如通过调用flushclose,或删除指针delete preproc;。如果可能的话,最好还是不要使用在堆上分配的对象。

您也可以通过调用

fstream设置为无缓冲模式
preproc->rdbuf()->pubsetbuf(NULL, 0); // nullptr for C++11
打开流后立即打开,虽然这不太可能是你想要的。

如果必须使用堆,使用C ++ 11,您可以利用std::unique_ptr / std::shared_ptr。如果你遇到C ++ 98,那么还有std::auto_ptr(告诫者)。