2012-01-10 135 views
0

我正在尝试一个相当简单的程序来测试二进制输入/输出。我基本上写了一个头文件(字符串)和一些数据(双打)的文件。代码如下:C++中的二进制输入/输出

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


int main() { 
    typedef std::ostream_iterator<double> oi_t; 
    typedef std::istream_iterator<double> ii_t; 
    std::ofstream ofs("data.bin", std::ios::in); 
    //-If file doesn't exist, create a new one now 
    if(!ofs) { 
     ofs.open("data.bin", std::ios::out|std::ios::binary|std::ios::app); 
    } 
    else { 
     ofs.close(); 
     ofs.open("data.bin", std::ios::out|std::ios::binary|std::ios::app); 
    } 

    //-Write a header consisting of length of grid subdomain and its name 
    ///* 
    const std::string grid = "Header"; 
    unsigned int olen = grid.size(); 
    ofs.write(reinterpret_cast<const char*>(&olen), sizeof(olen)); 
    ofs.write(grid.c_str(), olen); 
    //*/ 

    //-Now write the data 
    ///* 
    std::vector<double> data_out; 
    //std::vector<std::pair<int, int> > cell_ids; 
    for(int i=0; i<100; ++i) { 
     data_out.push_back(5.0*double(i) + 100.0); 
    } 
    ofs << std::setprecision(4); 
    std::copy(data_out.begin(), data_out.end(), oi_t(ofs, " ")); 
    //*/ 
    ofs.close(); 

    //-Now read the binary file; first header then data 
    std::ifstream ifs("data.bin", std::ios::binary); 
    ///* 
    unsigned int ilen; 
    ifs.read(reinterpret_cast<char*>(&ilen), sizeof(ilen)); 
    std::string header; 
    if(ilen > 0) { 
     char* buf = new char[ilen]; 
     ifs.read(buf,ilen); 
     header.append(buf,ilen); 
     delete[] buf; 
    } 
    std::cout << "Read header: " << header << "\n"; 
    //*/ 

    ///* 
    std::vector<double> data_in; 
    ii_t ii(ifs); 
    std::copy(ii, ii_t(), std::back_inserter(data_in)); 
    std::cout << "Read data size: " << data_in.size() << "\n"; 
    //*/ 
    ifs.close(); 

    //-Check the result 
    ///* 
    for(int i=0; i < data_out.size(); ++i) { 
     std::cout << "Testing input/output element #" << i << " : " 
       << data_out[i] << " " << data_in[i] << "\n"; 
    } 
    std::cout << "Element sizes: " << data_out.size() << " " << data_in.size() << 
      "\n"; 
    //*/ 
    return 0; 
} 

的问题是,当我尝试写和读(再打印),同时头和失败的数据(我确认它不读取数据,然后,但正确显示标题)。但是,当我写出其中一个写入部分(标题和/或数据)时,它会正确显示该部分,指示读取工作。我相信我没有正确地阅读。也许我错过了seekg的用法。

+0

为我工作。我得到“读取标题:标题\ n读取数据大小:100 \ n”然后100测试输入/输出... – Naddiseo 2012-01-10 03:20:45

+0

适用于我,使用visual studio 2010 – shengy 2012-01-10 03:34:10

+0

这很奇怪。它不适合我。代码原样,打印出的数据读取大小为0的数据,因此它在后面的打印部分中出现段错误。我在Cygwin和Linux(RHEL5)上测试过。尚未在Windows上进行测试。 – 2012-01-10 04:02:01

回答

1

该代码对我来说运行良好。但是,你永远不会检查文件是否成功打开进行写入,因此它可能会在系统上无声无息地失败。当您打开你应该添加

if (!ofs) { 
    std::cout << "Could not open file for writing" << std::endl; 
    return 1; 
} 

,同样的事情,你打开ifs

if (!ifs) { 
    std::cout << "Could not open file for reading" << std::endl; 
    return 1; 
} 

或者类似的规定之后。此外,我不明白为什么你检查文件是否存在,因为你不管它是否存在。

+0

感谢您的评论..但这是一个相对较小的问题,而不是解决我的整体阅读数据的实际问题,即标题和双打(我认为)。 – 2012-01-10 04:03:09

+0

你尝试过吗?你发布的代码适合我_unless_我无法打开文件'data.bin',在这种情况下它崩溃。 – 2012-01-10 04:07:54

+0

谢谢。你是对的。它在它打开时工作,并且当(ofs)失败(失败位)时崩溃。我解决这个问题。这给了我一些想法。 – 2012-01-10 05:22:58

0

这应该工作

#include <iostream> 
using std::cout; 
using std::cerr; 
using std::cin; 
using std::endl; 
#include <fstream> 
using std::ifstream; 
#include <cstdint> 

int main() { 

    ifstream fin; 
    fin.open("input.dat", std::ios::binary | std::ios::in); 
    if (!fin) { 
     cerr << "Cannot open file " << "input.dat" << endl; 
     exit(1); 
    } 

    uint8_t input_byte; 
    while (fin >> input_byte) { 
     cout << "got byte " << input_byte << endl; 
    } 

    return 0; 
}