具有python csv.dictreader功能的c ++ csv阅读器

时间:2015-03-11 09:09:35

标签: c++ csv

是否有任何用于在C ++中读取csv文件的库或示例,如Python中的csv模块?

我需要的是一个函数来读取一个csv文件,并将一行中的每个列元素放在一个以标题名称作为键值的地图中。

1 个答案:

答案 0 :(得分:1)

我可以自己回答。我写了一篇CSVDict课程。

#include <iterator>
#include <iostream>
#include <fstream>
#include <sstream>
#include <vector>
#include <string>
#include <map>

class CSVDict {
public:
    CSVDict(std::string fileName, int headerRow) {
        file = std::ifstream(fileName);
        for (int i = 0; i < headerRow; i++){ readNextRow(file); }
        m_header = m_data;
    }
    std::string const& operator[](std::size_t index) const {
        return m_data[index];
    }
    std::string const& operator[](std::string index) const {
        return m_dataMap.find(index)->second;
    }
    bool readNextRowMap() {
        readNextRow(file);
        if (!file) return false;
        m_dataMap.clear();
        auto it_data = m_data.begin();
        for (auto it = m_header.begin(); it != m_header.end(); ++it) {
            m_dataMap[*it] = *it_data;
            ++it_data;
        }
        return true;
    }
private:
    void readNextRow(std::istream& str) {
        std::string         line;
        std::getline(str, line);
        if (!str) return;

        std::stringstream   lineStream(line);
        std::string         cell;

        m_data.clear();
        while (std::getline(lineStream, cell, ';')) {
            m_data.push_back(cell);
        }
    }
    std::vector<std::string>    m_data;
    std::vector<std::string>    m_header;
    std::map<std::string, std::string> m_dataMap;
    std::ifstream file;
};


int main()
{
    CSVDict              dict("1.csv", 2);
    while (dict.readNextRowMap()) {
        std::cout << dict[0] << " " << dict[1] << " " << dict[2] << " " << dict[3] << " " << dict[4] << " " << dict[5] << " " << dict[6] << "\n";
    }

    CSVDict              dict1("1.csv", 2);
    dict1.readNextRowMap();
    std::cout << dict1["ipField"] << " " << dict1["mdBeamEnergy"] << " " << dict1["mdBeamCurrent"] << " " << dict1["mcoBeamSizeId"] << " " << dict1["mdGantryAngle"] << " " << dict1["miLayerNumber"] << "\n";
    dict1.readNextRowMap();
    std::cout << dict1["ipField"] << " " << dict1["mdBeamEnergy"] << " " << dict1["mdBeamCurrent"] << " " << dict1["mcoBeamSizeId"] << " " << dict1["mdGantryAngle"] << " " << dict1["miLayerNumber"] << "\n";
    dict1.readNextRowMap();
    std::cout << dict1["ipField"] << " " << dict1["mdBeamEnergy"] << " " << dict1["mdBeamCurrent"] << " " << dict1["mcoBeamSizeId"] << " " << dict1["mdGantryAngle"] << " " << dict1["miLayerNumber"] << "\n";

    dict.readNextRowMap();
    std::cout << dict[0] << " " << dict[1] << " " << dict[2] << " " << dict[3] << " " << dict[4] << " " << dict[5] << " " << dict[6] << "\n";
    return 0;
}

示例csv文件:

#VALUES;;;;;;
ipField;mdBeamEnergy;mdBeamCurrent;mcoBeamSizeId;mdGantryAngle;miLayerNumber;mbRoomSwitchingLayer
24.30815;172.152971;24.30815;4;65;1;1
24.30815;172.152971;24.30815;4;65;2;0
24.30815;172.152971;24.30815;4;65;3;0
24.30815;172.152971;24.30815;4;65;4;0
24.30815;172.152971;24.30815;4;65;5;0
24.30815;172.152971;24.30815;4;65;6;0
24.30815;172.152971;24.30815;4;65;7;0
24.30815;172.152971;24.30815;4;65;8;0

用法(参见示例中的main函数):

类构造函数需要具有csv文件名和csv标题行号 每个readNextRowMap获取csv文件中下一行的值 您可以通过数字索引或标题名称

来处理这些值

缺点:

csv文件必须有一个标题行