使用带有int作为字符类型的iostreams可以吗?

时间:2011-03-31 08:46:23

标签: c++ iostream

当我试图找到this question的答案时,我写了这个小测试程序:

#include <iostream>
#include <fstream>
#include <vector>
#include <iterator>
#include <algorithm>

void writeFile() {
    int data[] = {0,1,2,3,4,5,6,7,8,9,1000};

    std::basic_ofstream<int> file("test.data", std::ios::binary);
    std::copy(data, data+11, std::ostreambuf_iterator<int>(file));
}

void readFile() {
    std::basic_ifstream<int> file("test.data", std::ios::binary);
    std::vector<int> data(std::istreambuf_iterator<int>(file),
        (std::istreambuf_iterator<int>()));

    std::copy(data.begin(), data.end(), 
              std::ostream_iterator<int>(std::cout, " "));
    std::cout << std::endl;
}


int main()
{
    writeFile();
    readFile();

    return 0;
}

它按预期工作,将数据写入文件,并在读取文件后正确打印:

0 1 2 3 4 5 6 7 8 9 1000

但是,我不确定是否存在任何陷阱(除了字节问题,在处理二进制数据时总会有这些问题)?这是允许的吗?

2 个答案:

答案 0 :(得分:4)

  

它按预期工作。

我不确定你在期待什么...

  

这是允许的吗?

这可能不便携。 Streams依赖于char_traits以及仅在charwchar_t标准中定义的方面。一个实现可以提供更多,但我的赌注是你依赖于这些模板的最小默认实现而不是int的有意识实现。如果更深入的使用会导致问题,我不会感到惊讶。

答案 1 :(得分:2)

在任何事物上实例化任何iostream类或basic_string 但是char或wchar_t,没有提供特定的自定义特征类, 是未定义的行为;我见过的大多数库都定义了它 做某事,但这个定义通常没有指定,而且是 VC ++和g ++之间存在差异(我看过两个案例)。如果你 定义和使用自己的traits类,一些功能应该 工作

几乎所有格式化的插入器和提取器(<<>>运营商),istreamostream委托各个方面 现场;如果使用其中任何一个,你将不得不采取措施 确保这些工作也是如此。 (这通常意味着提供一个新的 numpunct facet。)

即使您只使用streambuf(如您的示例所示),filebuf 使用codecvt方面。并且不需要提供实现 一个codecvt,如果确实如此,它可以做任何它想要的东西 它。因为filebuf总是在{和} {1}}之间写入和读取char 文件,这个翻译必须做点什么。我其实很喜欢 因为这个原因,你的代码很有用。但你还是没有 知道磁盘上实际是什么,这意味着你无法记录它, 这意味着将来某个时候你将无法阅读它。

如果您的目标是编写二进制数据,那么您的第一步应该是 定义二进制格式,然后写入读写函数 实现它。可能使用iostream&lt;&lt;和&gt;&gt;语法,和 可能使用basic_streambuf<char>作为实际输入和 输出;一个basic_streambuf<char>,你已经仔细地了解了 “C”语言环境。或者不是定义自己的二进制格式,只需使用 现有的,如XDR。 (所有这一段都假设你想要 保存数据,稍后再读。如果这些只是临时文件, 用于在单次运行期间将临时内部数据溢出到磁盘,以及 将在程序执行结束时删除,更简单的解决方案 是有效的。)