解析选项卡分隔数据

时间:2011-05-10 02:06:15

标签: c++

我有一个文本文件(~10GB),格式如下:

data1<TAB>data2<TAB>data3<TAB>data4<NEWLINE>

我想浏览它并仅在data2上进行处理。在C ++中提取data2的最佳(最快)方法是什么。

编辑:添加NEWLINE

6 个答案:

答案 0 :(得分:4)

逐行读取文件。对于每一行,在选项卡上拆分。这将为您提供包含字段的数组,允许您使用第二个字段(data2)。

答案 1 :(得分:2)

这听起来像是shell工具等更高级工具的工作:

cut -f2           # from stdin
cut -f2 <my_file  # from file

但是,你也可以用C ++做到这一点:

void parse(std::istream& in)
{
    std::string word;
    while( in ) {
        std::cin >> word;  // throwaway 1
        std::cin >> word;  // data2
        process(word);
        std::cin >> word >> word;  // throwaway 3 and 4
    }
}

// ...
parse(std::cin);
std::ifstream file("my_file");
parse(file);

答案 2 :(得分:1)

好吧,打开一个文件流(应该能够处理10gig文件),然后跳转到第一个选项卡('\t'之后),读取您的数据,然后跳到下一个换行符并重复

#include <fstream>
#include <string>

int main(){
  std::fstream fin("your_file.txt");

  while(fin){
    std::string data2;
    char sink = '\0';

    // skip to first tab
    fin.ignore(1024,'\t');

    fin >> data2;
    // do stuff with data2

    // skip to next line
    fin.ignore(1024,'\n');
  }
}

答案 3 :(得分:1)

一次读取一行文件。从那里解析标签很简单。您可以使用类似strtok()或类似例程的内容。

答案 4 :(得分:1)

由于文件大小相当,您可以考虑使用一种技术,使您可以将I / O与处理重叠。作为回应,你提到你正在研究linux。如果您使用的是内核2.6或更高版本,则可以考虑使用Linux异步I / O(AIO)。具体来说,您可以使用aio_read对某些读取请求进行排队,然后使用aio_suspend等待一个(或多个)请求结束。当请求完成时,您将使用普通char *扫描缓冲区以找到您感兴趣的数据。对于您发现的每一段数据,您可以创建一个std :: string(尽管避免复制可能是有益的)并且处理它。扫描一个块后,您将对其进行重新排队以从文件中读取另一个块。在处理完文件中的每个块之前,请继续执行此操作。

此方法的代码将比逐行读取文件更复杂,但速度可能会快得多。

答案 5 :(得分:0)

你可以像其他人建议的那样使用iostream。另一种方法是简单地使用fscanf。例如:

#include <stdio.h>

...

FILE* fp = fopen(path_to_file, "r");
char[256] data;

while(fscanf(fp, "%*s<tab>%s<tab>%*s<tab>%*s", data))
{
   do what you want with your data
}