C ++逐行读取文件,然后使用分隔符拆分每一行

时间:2015-04-17 06:59:36

标签: c++

我已经搜索过并且很好地掌握了上一篇文章中的解决方案,但我仍然陷入困境。

我的问题是“randomstring TAB number TAB number NL”

我的数据是“数字(空格结构空间)数字(空格结构空间)句子”

我已经编辑了下面的代码,但仍然无法让它100%工作,因为getline的参数是(stream,string,delimiter)。

出于某种原因,它只获得句子的第一个单词,而不是其余的单词。

上一篇文章


我想逐行读取一个txt文件,在读完每一行之后,我想根据选项卡“\ t”拆分该行,并将每个部分添加到结构中的元素。

我的结构是1 * char和2 * int

struct myStruct
{
    char chr;
    int v1;
    int v2;
}

其中chr可以包含多个字符。

一行应该是这样的:

randomstring TAB编号TAB编号NL

std::ifstream file("plop");
std::string   line;

while(std::getline(file, line))
{
    std::stringstream   linestream(line);
    std::string         data;
    int                 val1;
    int                 val2;

    // If you have truly tab delimited data use getline() with third parameter.
    // If your data is just white space separated data
    // then the operator >> will do (it reads a space separated word into a string).
    std::getline(linestream, data, '\t');  // read up-to the first tab (discard tab).

    // Read the integers using the operator >>
    linestream >> val1 >> val2;
}

2 个答案:

答案 0 :(得分:0)

在以下代码行中,数据变量将保留整行。并且会消耗linestream,因此进一步的读数不会产生任何结果。

std::getline(linestream, data, '\t');  // read up-to the first tab (discard tab).

相反,你可以像这样工作

    while (std::getline(file, line))
    {
        int token1 = std::stoi(line.substr(0, line.find(" : ")));
        line.erase(0, line.find(" : ") + 3);

        int token2 = std::stoi(line.substr(0, line.find(" : ")));
        line.erase(0, line.find(" : ") + 3);

        std::string token3 = line;
    }

答案 1 :(得分:0)

你的问题究竟是什么?

//Title of this code
//clang 3.4

#include <iostream>
#include <string>
#include <iterator>
#include <algorithm>
#include <sstream>
#include <vector>

struct Data
{
    int n1;
    int n2;
    std::string sequence;
};

std::ostream& operator<<(std::ostream& ostr, const Data& data)
{
    ostr << "{" << data.n1 << "," << data.n2 << ",\"" << data.sequence << "\"}";
    return ostr;
}

std::string& ltrim(std::string& s, const char* t = " \t")
{
    s.erase(0, s.find_first_not_of(t));
    return s;
}

std::string& rtrim(std::string& s, const char* t = " \t")
{
    s.erase(s.find_last_not_of(t) + 1);
    return s;
}

std::string& trim(std::string& s, const char* t = " \t")
{
    return ltrim(rtrim(s, t), t);
}

int main()
{
    std::string file_content{
        "1\t1\t\n"
        "2\t2\tsecond sequence\t\n"
        "3\t3\tthird sequence\n"};

    std::istringstream file_stream{file_content};
    std::string line;
    std::vector<Data> content;
    while(std::getline(file_stream, line))
    {
        std::istringstream line_stream{line};
        Data data{};
        if(!(line_stream >> data.n1 >> data.n2))
        {
            std::cout << "Failed to parse line (numbers):\n" << line << "\n";
            break;
        }

        auto numbers_end = line_stream.tellg();
        if(numbers_end == -1)
        {
            std::cout << "Failed to parse line (sequence):\n" << line << "\n";
            break;
        }

        data.sequence = line.substr(numbers_end);
        trim(data.sequence);

        content.push_back(std::move(data));
    }

    std::copy(content.cbegin(), content.cend(),
        std::ostream_iterator<Data>(std::cout, "\n"));
}

Live

Live with colons