C++流 get unget 不是 nop 吗?

发布于 2024-12-12 01:30:44 字数 1408 浏览 0 评论 0原文

我有以下 C++ 程序,并在 Windows 7 上使用 Visual Studio 2008 运行它。我获取然后取消获取一个字符。这样做之后,文件位置就不同了。为什么?我该如何解决这个问题?


test.txt(如果需要,请下载以下链接)

/* Comment 1 */

/* Comment 2 */

#include <fstream>

int main (int argc, char ** argv) {
    char const * file = "test.txt";
    std::fstream fs(file, std::ios::in);
    std::streampos const before = fs.tellg();

    // replacing the following two lines with
    // char c = fs.peek(); results in the same problem
    char const c = fs.get();
    fs.unget();

    std::streampos const after = fs.tellg();
    fs.seekg(after);
    char const c2 = fs.get();
    fs.close();
    return 0;
}

  • c: 47 '/' char
  • c2: -1 'ÿ' char
  • 之前:{_Myoff=0 _Fpos =0 _Mystate=0 } std::fpos
  • 之后:{_Myoff=0 _Fpos=-3 _Mystate=0 } std::fpos

添加 | std::fstream::binary 到构造函数似乎可以解决问题。也许它与文件中的换行符有关?如果是这样,为什么它会影响甚至无法读取换行符的代码?

更新为寻找后位置并获得另一个角色。

看来通过记事本保存与通过 Vim 保存有区别。通过记事本保存使流正常工作。

我已将文件上传到 Google 文档,如果您想下载它:

https://docs.google.com/leaf?id=0B8Ufd7Rk6dvHZmYyZjgwYmItMTI3MC00MDljLWJjYTctMWMxYWM0ODk1MTE2&hl=en_US

I have the following C++ program and ran it using Visual Studio 2008 on Windows 7. I get and then unget a character. After doing so, the file position is different. Why? How do I get around this problem?


test.txt (download link below if you want)

/* Comment 1 */

/* Comment 2 */

#include <fstream>

int main (int argc, char ** argv) {
    char const * file = "test.txt";
    std::fstream fs(file, std::ios::in);
    std::streampos const before = fs.tellg();

    // replacing the following two lines with
    // char c = fs.peek(); results in the same problem
    char const c = fs.get();
    fs.unget();

    std::streampos const after = fs.tellg();
    fs.seekg(after);
    char const c2 = fs.get();
    fs.close();
    return 0;
}

  • c: 47 '/' char
  • c2: -1 'ÿ' char
  • before: {_Myoff=0 _Fpos=0 _Mystate=0 } std::fpos<int>
  • after: {_Myoff=0 _Fpos=-3 _Mystate=0 } std::fpos<int>

Adding | std::fstream::binary to the constructor seems to solve the problem. Perhaps it has to do with newlines in the file? If so, why does it affect code that doesn't even get close to reading a newline?

Updated with a seeking to the after position and getting another character.

It seems that saving via Notepad vs. Vim makes a difference. Saving via Notepad makes the stream work okay.

I have uploaded the file to google docs if you want to dl it:

https://docs.google.com/leaf?id=0B8Ufd7Rk6dvHZmYyZjgwYmItMTI3MC00MDljLWJjYTctMWMxYWM0ODk1MTE2&hl=en_US

如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。

扫码二维码加入Web技术交流群

发布评论

需要 登录 才能够评论, 你可以免费 注册 一个本站的账号。

评论(2

雨夜星沙 2024-12-19 01:30:44

好的,使用您的输入文件,我看到了与您相同的行为。经过一些实验,看起来该文件是 Unix 格式,然后编辑了 ^M 字符(至少这就是我能够重现它的方式)。

为了解决这个问题,我在 Vim 中编辑了文件,执行“:set ff=dos”,然后添加和删除了一个字符来弄脏文件,然后保存它。

Ok using your input file I see the same behavior you do. After some experimentation, it looks like the file was in Unix format, then had the ^M characters edited out (at least that's how I was able to reproduce it).

To fix it, I edited the file in Vim, executed ":set ff=dos", then added and deleted a character to dirty the file, then saved it.

比忠 2024-12-19 01:30:44

文件位置的行为符合预期:

// unget.cpp
#include <fstream>
#include <iostream>
int main ()
{
    char const * file = "test.txt";
    std::fstream fs(file, std::fstream::in);

    std::cout << fs.tellg() << std::endl; // 0
    char c = fs.get();
    std::cout << fs.tellg() << std::endl; // 1
    fs.unget();
    std::cout << fs.tellg() << std::endl; // 0

    fs.close();
    return 0;
}

构建并运行:

$ clang++ unget.cpp 
$ ./a.out 
0
1
0

或者,我不明白问题出在哪里。

The file position behaves as expected:

// unget.cpp
#include <fstream>
#include <iostream>
int main ()
{
    char const * file = "test.txt";
    std::fstream fs(file, std::fstream::in);

    std::cout << fs.tellg() << std::endl; // 0
    char c = fs.get();
    std::cout << fs.tellg() << std::endl; // 1
    fs.unget();
    std::cout << fs.tellg() << std::endl; // 0

    fs.close();
    return 0;
}

Build and run:

$ clang++ unget.cpp 
$ ./a.out 
0
1
0

Or, I don't understand where is the problem.

~没有更多了~
我们使用 Cookies 和其他技术来定制您的体验包括您的登录状态等。通过阅读我们的 隐私政策 了解更多相关信息。 单击 接受 或继续使用网站,即表示您同意使用 Cookies 和您的相关数据。
原文