C 读取大文件,其中有几个部分

C++ reading big file with several section

本文关键字:有几个部 读取 文件      更新时间:2023-10-16

我正在尝试在C 中编写一个简单的程序,该程序给出了一个大的数据文件,分别为x,y,z,有一个标题,其中写有书面的标题INT随后的数据大小。此数字之前是字符串" i =",您可以在此处可视化文件http://dpaste.com/19hqy58

我编写了一个读取第一部分的代码,但在另一部分中,代码失败了……这是代码:

# include <iostream>
# include <fstream>
# include <iomanip>
# include <string>
# include <sstream>
# include <cstdlib>
# include <cmath>
# include <vector>
# include <exception>
# include <algorithm>
# include <cstring>
//----------------------------------------------------------------------------------------
using namespace std;
//--- Function prototipes 

void readData(vector<vector<vector<double>>>*, string& , int&);

//---
int main(int args, char* argv[]){
  string time,root ;    
  string filename = "stangle.000000000.dat" 
  int N;    
       
  vector<vector<vector<double>>>* ptrData ;
                 
  ptrData = new vector<vector<vector<double>>>(10); 
     
  readData(ptrData, filename, N);
           
  return 0;
}

//---
//
   
void readData( vector<vector<vector<double>>>* data,  string& file, int& size){
      unsigned int header = 3;
      string tmp, row ;
      ifstream inputFile;
      
      cout << file << endl;
      try
      {
            inputFile.open(file, ios::in);
      }
      catch(...) 
      {
            cerr << "Error occurred opening file " << file << " program terminate!" << endl;
            exit(1);
      }
      
      int indx=0;
                 
    int k=0;
      
    while(getline(inputFile,row) && (k <= 1)){
     if(k==0)
      while( k++ <= header-1 && getline(inputFile,row)){ 
            istringstream elem(row);
            if(k == header ){
                  while(elem >> tmp){
                             if(strcmp(tmp.c_str(),"I=" )== 0){
                               elem >> tmp ; 
                               size = atoi(tmp.c_str());
                             }
                  }
           }
     }
     else
     {
       int w = 0 ;
       while( w++ <= header-1 && getline(inputFile,row)){ 
            istringstream elem(row);
            if(w == header-1 ){
                  while(elem >> tmp){
                             if(strcmp(tmp.c_str(),"I=" )== 0){
                               elem >> tmp ; 
                               size = atoi(tmp.c_str());
                             }
                  }
           }
       }
      }
      cout << "size = " << size << endl;
      
      k=0;
      data->resize(size*3) ;
      data->at(k).resize(size*3) ;
      
      for(int i=0; i<size; i++)                // resize vector ! 
                  data->at(k)[i].resize(3) ;
      
      int j=0;
      while(getline(inputFile,row) && j < size){
            istringstream elem(row);
            for(int i=0; i < 3; i++)
                  elem >> data->at(k)[j].at(i); 
            elem >> tmp ;                    // 4th columns to skip
            j++;
      }
      
        
      k++ ;
   }   
}

有人可以帮我吗?谢谢你

这里的样本示例

VARIABLES= "X","Y","Z","T" 
 
 
ZONE I=    10  F=POINT  T="time=      0.0000000000 " 
  0.386493318E-01  0.128555549E-01  0.340086408E-01  0.312500005E-02
  0.383133255E-01  0.138539430E-01  0.340525173E-01  0.312500005E-02
  0.382215269E-01  0.148848109E-01  0.340615511E-01  0.312500005E-02
  0.377206728E-01  0.157320835E-01  0.342985764E-01  0.312500005E-02
  0.370856710E-01  0.163890962E-01  0.346758589E-01  0.312500005E-02
  0.365753844E-01  0.170070678E-01  0.349843502E-01  0.312500005E-02
  0.362384841E-01  0.179224834E-01  0.353175104E-01  0.312500005E-02
  0.362287983E-01  0.188916922E-01  0.356959850E-01  0.312500005E-02
  0.361620262E-01  0.199434906E-01  0.359359272E-01  0.312500005E-02
  0.361897759E-01  0.210271589E-01  0.360902399E-01  0.312500005E-02
 
 
ZONE I=     6  F=POINT  T="time=      0.0000000000 " 
  0.435949154E-01  0.254055243E-01 -0.491932891E-01  0.312500005E-02
  0.434608348E-01  0.254306290E-01 -0.482175574E-01  0.312500005E-02
  0.432049297E-01  0.259031206E-01 -0.474165194E-01  0.312500005E-02
  0.427575074E-01  0.264129750E-01 -0.467625186E-01  0.312500005E-02
  0.420416631E-01  0.268291328E-01 -0.463280752E-01  0.312500005E-02
  0.411394201E-01  0.266988464E-01 -0.461011454E-01  0.312500005E-02

 
 
ZONE I=     4  F=POINT  T="time=      0.0000000000 " 
  0.435949154E-01  0.254055243E-01 -0.491932891E-01  0.312500005E-02
  0.434608348E-01  0.254306290E-01 -0.482175574E-01  0.312500005E-02
  0.432049297E-01  0.259031206E-01 -0.474165194E-01  0.312500005E-02
  0.427575074E-01  0.264129750E-01 -0.467625186E-01  0.312500005E-02`

我建议对您的程序进行重新设计。

您的输入文件包含记录块。因此,以这种方式设计。

struct Record
{
  double m_values[4]; // These could be itemized if you know their purpose
};
struct Block
{
  std::string m_f;
  double      m_time;
  std::vector<Record> m_records;
};

下一步将是每个类中的operator>>在数据成员中读取。

struct Record
{
  //...
  friend std::istream& operator>>(std::istream& input, Record& r);
};
std::istream& operator>>(std::istream& input, Record& r)
{
  input >> r.m_values[0];
  input >> r.m_values[1];
  input >> r.m_values[2];
  input >> r.m_values[3];
  return input;
}
struct Block
{
  //...
  friend std::istream& operator>>(std::istream& input, Block& b);
};
std::istream& operator>>(std::istream& input, Block& b)
{
  std::string text;
  while (std::getline(input, text))
  {
    if (text.empty()) continue;
    static const char zone_key_text[] = "ZONE I=";
    std::string::size_type position = text.find(zone_key_text);
    if (position != 0) continue;
    std::istringstream text_stream(text.substr(sizeof(zone_key_text) - 1));
    int record_quantity = 0;
    text_stream >> record_quantity;
    // Parse remaining fields
    Record r;
    for (int i = 0; i < quantity; ++i)
    {
      input >> r;
      m_records.push_back(r);
    }
    //...
}

ZONE I=包含记录数。记录的数量各不相同,这是将std::vector用于记录的好指标。

读取文件然后变为:

std::string variables;
std::getline(inputFile, variables);
std::vector<Block> database;
Block b;
while (inputFile >> b)
{
  database.push_back(b);
}

您可能想解析变量文本行,然后使用std::map<char, Block>将变量与数据块相关联。