简体   繁体   English

如何以向量的向量作为其值来遍历 map?

[英]How can you iterate through a map with a vector of vectors as its value?

I'm trying to write a function that takes a "vector of vectors" and stores them inside a map.我正在尝试编写一个 function,它采用“向量的向量”并将它们存储在 map 中。 Essentially I want to store a series of SQL statements (values) inside a map with the table name as the key.本质上,我想在 map 中存储一系列 SQL 语句(值),表名作为键。

So for example: - table1 key will store all sql queries to be output to table1 - table2 key will store all sql queries to be output to table2 So for example: - table1 key will store all sql queries to be output to table1 - table2 key will store all sql queries to be output to table2

So far I've written this in a boost unit test where I declare std::vector<std::vector<std::string> > mapVector which stores my queries.到目前为止,我已经在一个 boost 单元测试中写了这个,我声明了std::vector<std::vector<std::string> > mapVector来存储我的查询。 Once that is populated, I want to store them inside std::map<std::string, std::vector<std::vector<std::string> > > mapQueries .填充后,我想将它们存储在std::map<std::string, std::vector<std::vector<std::string> > > mapQueries中。

Now, I have no problem with storing this data, it's just a matter of how to access the elements inside my mapQueries map.现在,我对存储这些数据没有任何问题,只是如何访问我的mapQueries map 中的元素。

BOOST_AUTO_TEST_CASE(mapTestVects){
    std::string tableName = "ENCODER1";
    std::vector<std::string> crt1;
    std::vector<std::string> crt2;
    std::vector<std::string> insertColumns1;
    std::vector<std::string> insertValues1;
    std::vector<std::string> insertColumns2;
    std::vector<std::string> insertValues2;
    std::vector<std::vector<std::string> > mapVector;

    std::string crt1Array[256] = {"ID", "RECORDTIME", "TYPE", "TIMESTAMP", "ENCODER1", "ENCODER2", "ENCODER3", "ENCODER4", "ENCODER5"};
    std::string crt2Array[256] = {"INTEGER", "BIGINT", "INTEGER", "BIGINT", "INTEGER", "INTEGER", "INTEGER", "INTEGER", "INTEGER"};
    std::string insertColumns1Array[256] = {"ID", "RECORDTIME", "TYPE", "TIMESTAMP", "ENCODER1", "ENCODER2", "ENCODER3", "ENCODER4", "ENCODER5"};
    std::string insertValues1Array[256] = {"1", "2", "3", "4", "5", "6", "7", "8", "9"};
    std::string insertColumns2Array[256] = {"ID", "RECORDTIME", "TYPE", "TIMESTAMP", "ENCODER1", "ENCODER2", "ENCODER3", "ENCODER4", "ENCODER5"};
    std::string insertValues2Array[256] = {"10", "11", "12", "13", "14", "15", "16", "17", "18"};

    for(int i = 0; i < 9; i++){
        crt1.push_back(crt1Array[i]);
        crt2.push_back(crt2Array[i]);
        insertColumns1.push_back(insertColumns1Array[i]);
        insertValues1.push_back(insertValues1Array[i]);
        insertColumns2.push_back(insertColumns2Array[i]);
        insertValues2.push_back(insertValues2Array[i]);

    }
    mapVector.push_back(insertColumns1);
    mapVector.push_back(insertValues1);
    mapVector.push_back(insertColumns2);
    mapVector.push_back(insertValues2);

    std::map<std::string, std::vector<std::string> > blah;
    std::map<std::string, std::vector<std::vector<std::string> > > mapQueries;

    mapQueries.insert(std::pair<std::string, std::vector<std::vector<std::string> > >("table1", mapVector) );

    std::map<std::string, std::string>::iterator it = mapQueries.begin();
    while(it != mapQueries.end()){
        std::cout << it->first << " :: " << it->second <<std::endl;
        it++;
    }

I try to iterate through it using std::map<std::string, std::string>::iterator however I get the following compiler error:我尝试使用std::map<std::string, std::string>::iterator它但是我得到以下编译器错误:

error: conversion from ‘std::map<std::__cxx11::basic_string<char>, std::vector<std::vector<std::__cxx11::basic_string<char> > > >::iterator {aka std::_Rb_tree_iterator<std::pair<const std::__cxx11::basic_string<char>, std::vector<std::vector<std::__cxx11::basic_string<char> > > > >}’ to non-scalar type ‘std::map<std::__cxx11::basic_string<char>, std::__cxx11::basic_string<char> >::iterator {aka std::_Rb_tree_iterator<std::pair<const std::__cxx11::basic_string<char>, std::__cxx11::basic_string<char> > >}’ requested
     std::map<std::string, std::string>::iterator it = mapQueries.begin();

error: no match for ‘operator!=’ (operand types are ‘std::map<std::__cxx11::basic_string<char>, std::__cxx11::basic_string<char> >::iterator {aka std::_Rb_tree_iterator<std::pair<const std::__cxx11::basic_string<char>, std::__cxx11::basic_string<char> > >}’ and ‘std::map<std::__cxx11::basic_string<char>, std::vector<std::vector<std::__cxx11::basic_string<char> > > >::iterator {aka std::_Rb_tree_iterator<std::pair<const std::__cxx11::basic_string<char>, std::vector<std::vector<std::__cxx11::basic_string<char> > > > >}’)
     while(it != mapQueries.end()){

The reason I have stored my queries as vectors, is because I am using sqlite3 and need to track type, values, and table data in order to bind and execute queries.我将查询存储为向量的原因是因为我使用 sqlite3 并且需要跟踪类型、值和表数据以绑定和执行查询。 I am also using C++98 (required).我也在使用 C++98(必需)。

  1. mapQueries is std::map<std::string, std::vector<std::vector<std::string> > > , not std::map<std::string, std::string> , so use mapQueriesstd::map<std::string, std::vector<std::vector<std::string> > > ,而不是std::map<std::string, std::string> ,所以使用
std::map<std::string, std::vector<std::vector<std::string> > >::iterator it = mapQueries.begin();

or much simpler (but only since C++11)或更简单(但仅从 C++11 开始)

auto it = mapQueries.begin();

instead of代替

std::map<std::string, std::string>::iterator it = mapQueries.begin();
  1. You can't print vector this way (unless you overload opeator<< How to print out the contents of a vector? ):您不能以这种方式打印向量(除非您重载opeator<< 如何打印出向量的内容? ):
std::cout << it->first << " :: " << it->second <<std::endl;
//                                  ^^^^^^^^^^ vector

Here https://stackoverflow.com/a/10758845/3365922 are lots of ways to do this. https://stackoverflow.com/a/10758845/3365922有很多方法可以做到这一点。 These are examples valid for C++98:这些是适用于 C++98 的示例:

// A.
for (std::vector<std::vector<std::string> >::iterator it1 = it->second.begin(); it1 != it->second.end(); ++it1)
    for (std::vector<std::string>::iterator it2 = it1->begin(); it2 != it1->end(); ++it2)
        std::cout << *it2 << " ";

// B.
for (size_t i = 0; i < it->second.size(); ++i)
    for (size_t j = 0; j < it->second[i].size(); ++j)
        std::cout << it->second[i][j] << " ";

You cannot use an iterator for a different type to loop through mapQueries .您不能使用不同类型的迭代器来循环mapQueries You maybe should loop through mapQueries , get the key (type std::string ) and value (type vector<vector<string> > ), then loop through the vector of vectors, then loop each vector inside that.您可能应该遍历mapQueries ,获取键(类型std::string )和值(类型vector<vector<string> > ),然后遍历向量向量,然后循环其中的每个向量。 Like so:像这样:

typedef vector<string> vs_t;
typedef vector<vs_t> vvs_t;
typedef map<string, vvs_t> mapQueries_t;
for (mapQueries_t::iterator i = mapQueries.begin(); i != mapQueries.end(); ++i) {
    string& key = i->first;
    for (vvs_t::iterator j = i->second.begin(); j != i->second.end(); ++j) {
        for (vs_t::iterator k = j->begin(); k != j->end(); ++k) {
            string& value = *k;
            // use key and value
        }
    }
}

I'm using references to prevent copies.我正在使用引用来防止复制。

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM