Преобразование вектора во вложенную карту в C ++ - PullRequest
1 голос
/ 12 июля 2020

У меня есть вектор строк в следующем формате на C ++

word1_word2_word3: val

Здесь word1 может быть любой строкой в ​​{str1, str2, str3, str4} word2 может быть любой строкой из {anotherstr1, anotherstr2,...,anotherstr12} и word3 может быть любой строкой из {yetanotherstr1, yetanotherstr2}

Все виды перестановок и комбинаций указанной выше строки могут быть заполнены в векторе и будут иметь строковое значение, соответствующее этой комбинации

My Цель состоит в том, чтобы создать вектор карты из вектора строки в следующем формате

anotherstr1 :  str1: yetanotherstr1 : its_value
                     yetanotherstr2 : its_value

               str2: yetanotherstr1 : its_value
                     yetanotherstr2 : its_value
               ...
               ...
               str4: yetanotherstr1 : its_value
                     yetanotherstr2 : its_value
anotherstr2  : str1: yetanotherstr1 : its_value
                     yetanotherstr2 : its_value
               str2: yetanotherstr1 : its_value
                     yetanotherstr2 : its_value
               ...
               ...
               str4: yetanotherstr1 : its_value
                     yetanotherstr2 : its_value
.........
.........
anotherstr12 : str1: yetanotherstr1 : its_value
                     yetanotherstr2 : its_value
               str2: yetanotherstr1 : its_value
                     yetanotherstr2 : its_value
                ...
                ...
               str4: yetanotherstr1 : its_value
                     yetanotherstr2 : its_value

Все эти строковые значения являются динамическими c.

Я пробовал это сделать. Найдите псевдокод

for (each vector)
{
     parse_params_in_string(*i, word1, word2, word3);
     std::map outermap;
     std::map innermap;
     for(each word 1 and word3 combination)
            build_map_elements
     outermap.insert(innermap)
     ..
}

Но приведенный выше код каждый раз создает fre sh внутреннюю карту и добавляет ее к внешней карте, что неверно. Как я могу добавить эти значения на внешнюю карту?

Заранее спасибо

1 Ответ

1 голос
/ 12 июля 2020

Глядя на желаемый результат, я решил создать std::map из std::map из std::map с ключом и значением std::string

Я приказываю, чтобы иметь возможность протестировать код, мы сначала создаем std::vector из std::string и используем указанные вами слова в качестве входных.

Для данных данного примера мы получим std::vector с 96 элементами. Итак, 12 * 4 * 2 строки.

Следующая часть - это то, что вы хотите. Сначала мы разбиваем std::string. Я опубликовал уже много ответов о том, как разбить строку. См., Например, здесь .

На этот раз я буду использовать регулярное выражение, потому что ваш вопрос не о разбиении строки, а о том, как создать словарь.

В любом случае , мы заполняем std::vector разделенными подстроками, используя std::sregex_token_iterator. Итак, наконец, ваши слова будут в этом векторе подстроки.

Мы применим эту операцию для всех std::string s в std::vector в простом диапазоне, основанном на l oop.

После того, как мы вернули слова, нам нужно добавить данные на карту.

И здесь мы будем использовать оператор индекса std::maps s. Пожалуйста, прочтите внимательно об этом здесь . И, пожалуйста, прочтите особенно

Возвращает ссылку на значение, которое сопоставлено с ключом, эквивалентным ключу, выполняя вставку, если такой ключ еще не существует.

Это означает, что если вы используете оператор индекса, и значение еще не находится в std::map, оно будет добавлено. И в любом случае, если ключ уже был там или был только что создан, будет возвращена ссылка на этот фрагмент данных. И для вложенной карты мы, конечно, можем каскадировать оператор индекса. Итак, в строке из приведенного ниже кода:

mapData[substrings[1]][substrings[0]][substrings[2]] = substrings[3];

Сначала будут созданы самые внешние данные, и в любом случае будет возвращена ссылка. То же самое происходит сейчас для следующего внутреннего std::map и т. Д.

Таким образом, заполнение такой вложенной карты может быть выполнено однострочным.

Это действительно мощная операция.

И последнее, но не менее важное: мы будем печатать данные на экране по запросу OP.

Мы делаем это немного приятнее, не повторяя уже показанные данные.

Пожалуйста см. полный код ниже. Основная часть, которая важна для вас, - это всего 4 строки кода.

#include <iostream>
#include <vector>
#include <string>
#include <algorithm>
#include <iterator>
#include <regex>
#include <map>
#include <iomanip>

// We want to build a vector of test strings
// For this we will use word pools
std::vector<std::string> word1Pool{ "str1", "str2", "str3", "str4" };
std::vector<std::string> word2Pool{ "anotherstr01",  "anotherstr02", "anotherstr03", "anotherstr04", "anotherstr05", 
    "anotherstr06","anotherstr07", "anotherstr08", "anotherstr09", "anotherstr10", "anotherstr11", "anotherstr12" };
std::vector<std::string> word3Pool{ "yetanotherstr1", "yetanotherstr2" };

// A regex to split the strings
const std::regex re{ R"([a-zA-Z0-9]+)" };


// Some driver code
int main() {

    // First, we build a string with all possible combinations of word fragments. Overall: 12*4*2 = 96
    size_t counter{};

    // Here we will build some demo source data. A vector with all combinations of the given words
    std::vector<std::string> sourceData{};

    for (const std::string& word1 : word1Pool)
        for (const std::string& word2 : word2Pool)
            for (const std::string& word3 : word3Pool)
                sourceData.emplace_back(word1 + "_" + word2 + "_" + word3 + " : itsvalue" + std::to_string(++counter));

    // Show the demo stings on the screen
    std::copy(sourceData.begin(), sourceData.end(), std::ostream_iterator<std::string>(std::cout, "\n"));

    // ----------------------------------------------------------------------------------------------
    // This will be our nested map. It will hold the target data
    std::map<std::string, std::map<std::string, std::map<std::string, std::string>>> mapData;

    // Build the data in the map
    for (const std::string& line : sourceData) {

        // Split the line with demo data
        std::vector substrings(std::sregex_token_iterator(line.begin(), line.end(), re), {});

        // Add data to map
        mapData[substrings[1]][substrings[0]][substrings[2]] = substrings[3];
    }
    // ----------------------------------------------------------------------------------------------


    // Display resulting data on screen
    std::string oldKey1{}, oldKey2{}, oldKey3{};

    for (const auto& [key1, mapOuter] : mapData) {
        for (const auto [key2, mapInner] : mapOuter) {
            for (const auto [key3, dataInner] : mapInner) {


                std::cout << std::left << std::setw(12)
                    << ((oldKey1 == key1) ? std::string{} : key1) << ((oldKey1 == key1) ? "   " : " : ")  
                    << std::setw(4) 
                    << ((oldKey2 == key2) ? std::string{} : key2) << ((oldKey2 == key2) ? "  " : ": ")
                    << std::setw(14)
                    << ((oldKey3 == key3) ? std::string{} : key3) << ((oldKey3 == key3) ? "   " : " : ")
                    << dataInner << '\n';

                oldKey1 = key1;
                oldKey2 = key2;
                oldKey3 = key3;
            }
        }
    }
    return 0;
}

Вектор с тестовыми строками:

str1_anotherstr01_yetanotherstr1 : itsvalue1
str1_anotherstr01_yetanotherstr2 : itsvalue2
str1_anotherstr02_yetanotherstr1 : itsvalue3
str1_anotherstr02_yetanotherstr2 : itsvalue4
str1_anotherstr03_yetanotherstr1 : itsvalue5
str1_anotherstr03_yetanotherstr2 : itsvalue6
str1_anotherstr04_yetanotherstr1 : itsvalue7
str1_anotherstr04_yetanotherstr2 : itsvalue8
str1_anotherstr05_yetanotherstr1 : itsvalue9
str1_anotherstr05_yetanotherstr2 : itsvalue10
str1_anotherstr06_yetanotherstr1 : itsvalue11
str1_anotherstr06_yetanotherstr2 : itsvalue12
str1_anotherstr07_yetanotherstr1 : itsvalue13
str1_anotherstr07_yetanotherstr2 : itsvalue14
str1_anotherstr08_yetanotherstr1 : itsvalue15
str1_anotherstr08_yetanotherstr2 : itsvalue16
str1_anotherstr09_yetanotherstr1 : itsvalue17
str1_anotherstr09_yetanotherstr2 : itsvalue18
str1_anotherstr10_yetanotherstr1 : itsvalue19
str1_anotherstr10_yetanotherstr2 : itsvalue20
str1_anotherstr11_yetanotherstr1 : itsvalue21
str1_anotherstr11_yetanotherstr2 : itsvalue22
str1_anotherstr12_yetanotherstr1 : itsvalue23
str1_anotherstr12_yetanotherstr2 : itsvalue24
str2_anotherstr01_yetanotherstr1 : itsvalue25
str2_anotherstr01_yetanotherstr2 : itsvalue26
str2_anotherstr02_yetanotherstr1 : itsvalue27
str2_anotherstr02_yetanotherstr2 : itsvalue28
str2_anotherstr03_yetanotherstr1 : itsvalue29
str2_anotherstr03_yetanotherstr2 : itsvalue30
str2_anotherstr04_yetanotherstr1 : itsvalue31
str2_anotherstr04_yetanotherstr2 : itsvalue32
str2_anotherstr05_yetanotherstr1 : itsvalue33
str2_anotherstr05_yetanotherstr2 : itsvalue34
str2_anotherstr06_yetanotherstr1 : itsvalue35
str2_anotherstr06_yetanotherstr2 : itsvalue36
str2_anotherstr07_yetanotherstr1 : itsvalue37
str2_anotherstr07_yetanotherstr2 : itsvalue38
str2_anotherstr08_yetanotherstr1 : itsvalue39
str2_anotherstr08_yetanotherstr2 : itsvalue40
str2_anotherstr09_yetanotherstr1 : itsvalue41
str2_anotherstr09_yetanotherstr2 : itsvalue42
str2_anotherstr10_yetanotherstr1 : itsvalue43
str2_anotherstr10_yetanotherstr2 : itsvalue44
str2_anotherstr11_yetanotherstr1 : itsvalue45
str2_anotherstr11_yetanotherstr2 : itsvalue46
str2_anotherstr12_yetanotherstr1 : itsvalue47
str2_anotherstr12_yetanotherstr2 : itsvalue48
str3_anotherstr01_yetanotherstr1 : itsvalue49
str3_anotherstr01_yetanotherstr2 : itsvalue50
str3_anotherstr02_yetanotherstr1 : itsvalue51
str3_anotherstr02_yetanotherstr2 : itsvalue52
str3_anotherstr03_yetanotherstr1 : itsvalue53
str3_anotherstr03_yetanotherstr2 : itsvalue54
str3_anotherstr04_yetanotherstr1 : itsvalue55
str3_anotherstr04_yetanotherstr2 : itsvalue56
str3_anotherstr05_yetanotherstr1 : itsvalue57
str3_anotherstr05_yetanotherstr2 : itsvalue58
str3_anotherstr06_yetanotherstr1 : itsvalue59
str3_anotherstr06_yetanotherstr2 : itsvalue60
str3_anotherstr07_yetanotherstr1 : itsvalue61
str3_anotherstr07_yetanotherstr2 : itsvalue62
str3_anotherstr08_yetanotherstr1 : itsvalue63
str3_anotherstr08_yetanotherstr2 : itsvalue64
str3_anotherstr09_yetanotherstr1 : itsvalue65
str3_anotherstr09_yetanotherstr2 : itsvalue66
str3_anotherstr10_yetanotherstr1 : itsvalue67
str3_anotherstr10_yetanotherstr2 : itsvalue68
str3_anotherstr11_yetanotherstr1 : itsvalue69
str3_anotherstr11_yetanotherstr2 : itsvalue70
str3_anotherstr12_yetanotherstr1 : itsvalue71
str3_anotherstr12_yetanotherstr2 : itsvalue72
str4_anotherstr01_yetanotherstr1 : itsvalue73
str4_anotherstr01_yetanotherstr2 : itsvalue74
str4_anotherstr02_yetanotherstr1 : itsvalue75
str4_anotherstr02_yetanotherstr2 : itsvalue76
str4_anotherstr03_yetanotherstr1 : itsvalue77
str4_anotherstr03_yetanotherstr2 : itsvalue78
str4_anotherstr04_yetanotherstr1 : itsvalue79
str4_anotherstr04_yetanotherstr2 : itsvalue80
str4_anotherstr05_yetanotherstr1 : itsvalue81
str4_anotherstr05_yetanotherstr2 : itsvalue82
str4_anotherstr06_yetanotherstr1 : itsvalue83
str4_anotherstr06_yetanotherstr2 : itsvalue84
str4_anotherstr07_yetanotherstr1 : itsvalue85
str4_anotherstr07_yetanotherstr2 : itsvalue86
str4_anotherstr08_yetanotherstr1 : itsvalue87
str4_anotherstr08_yetanotherstr2 : itsvalue88
str4_anotherstr09_yetanotherstr1 : itsvalue89
str4_anotherstr09_yetanotherstr2 : itsvalue90
str4_anotherstr10_yetanotherstr1 : itsvalue91
str4_anotherstr10_yetanotherstr2 : itsvalue92
str4_anotherstr11_yetanotherstr1 : itsvalue93
str4_anotherstr11_yetanotherstr2 : itsvalue94
str4_anotherstr12_yetanotherstr1 : itsvalue95
str4_anotherstr12_yetanotherstr2 : itsvalue96

Вывод:

anotherstr01 : str1: yetanotherstr1 : itsvalue1
                     yetanotherstr2 : itsvalue2
               str2: yetanotherstr1 : itsvalue25
                     yetanotherstr2 : itsvalue26
               str3: yetanotherstr1 : itsvalue49
                     yetanotherstr2 : itsvalue50
               str4: yetanotherstr1 : itsvalue73
                     yetanotherstr2 : itsvalue74
anotherstr02 : str1: yetanotherstr1 : itsvalue3
                     yetanotherstr2 : itsvalue4
               str2: yetanotherstr1 : itsvalue27
                     yetanotherstr2 : itsvalue28
               str3: yetanotherstr1 : itsvalue51
                     yetanotherstr2 : itsvalue52
               str4: yetanotherstr1 : itsvalue75
                     yetanotherstr2 : itsvalue76
anotherstr03 : str1: yetanotherstr1 : itsvalue5
                     yetanotherstr2 : itsvalue6
               str2: yetanotherstr1 : itsvalue29
                     yetanotherstr2 : itsvalue30
               str3: yetanotherstr1 : itsvalue53
                     yetanotherstr2 : itsvalue54
               str4: yetanotherstr1 : itsvalue77
                     yetanotherstr2 : itsvalue78
anotherstr04 : str1: yetanotherstr1 : itsvalue7
                     yetanotherstr2 : itsvalue8
               str2: yetanotherstr1 : itsvalue31
                     yetanotherstr2 : itsvalue32
               str3: yetanotherstr1 : itsvalue55
                     yetanotherstr2 : itsvalue56
               str4: yetanotherstr1 : itsvalue79
                     yetanotherstr2 : itsvalue80
anotherstr05 : str1: yetanotherstr1 : itsvalue9
                     yetanotherstr2 : itsvalue10
               str2: yetanotherstr1 : itsvalue33
                     yetanotherstr2 : itsvalue34
               str3: yetanotherstr1 : itsvalue57
                     yetanotherstr2 : itsvalue58
               str4: yetanotherstr1 : itsvalue81
                     yetanotherstr2 : itsvalue82
anotherstr06 : str1: yetanotherstr1 : itsvalue11
                     yetanotherstr2 : itsvalue12
               str2: yetanotherstr1 : itsvalue35
                     yetanotherstr2 : itsvalue36
               str3: yetanotherstr1 : itsvalue59
                     yetanotherstr2 : itsvalue60
               str4: yetanotherstr1 : itsvalue83
                     yetanotherstr2 : itsvalue84
anotherstr07 : str1: yetanotherstr1 : itsvalue13
                     yetanotherstr2 : itsvalue14
               str2: yetanotherstr1 : itsvalue37
                     yetanotherstr2 : itsvalue38
               str3: yetanotherstr1 : itsvalue61
                     yetanotherstr2 : itsvalue62
               str4: yetanotherstr1 : itsvalue85
                     yetanotherstr2 : itsvalue86
anotherstr08 : str1: yetanotherstr1 : itsvalue15
                     yetanotherstr2 : itsvalue16
               str2: yetanotherstr1 : itsvalue39
                     yetanotherstr2 : itsvalue40
               str3: yetanotherstr1 : itsvalue63
                     yetanotherstr2 : itsvalue64
               str4: yetanotherstr1 : itsvalue87
                     yetanotherstr2 : itsvalue88
anotherstr09 : str1: yetanotherstr1 : itsvalue17
                     yetanotherstr2 : itsvalue18
               str2: yetanotherstr1 : itsvalue41
                     yetanotherstr2 : itsvalue42
               str3: yetanotherstr1 : itsvalue65
                     yetanotherstr2 : itsvalue66
               str4: yetanotherstr1 : itsvalue89
                     yetanotherstr2 : itsvalue90
anotherstr10 : str1: yetanotherstr1 : itsvalue19
                     yetanotherstr2 : itsvalue20
               str2: yetanotherstr1 : itsvalue43
                     yetanotherstr2 : itsvalue44
               str3: yetanotherstr1 : itsvalue67
                     yetanotherstr2 : itsvalue68
               str4: yetanotherstr1 : itsvalue91
                     yetanotherstr2 : itsvalue92
anotherstr11 : str1: yetanotherstr1 : itsvalue21
                     yetanotherstr2 : itsvalue22
               str2: yetanotherstr1 : itsvalue45
                     yetanotherstr2 : itsvalue46
               str3: yetanotherstr1 : itsvalue69
                     yetanotherstr2 : itsvalue70
               str4: yetanotherstr1 : itsvalue93
                     yetanotherstr2 : itsvalue94
anotherstr12 : str1: yetanotherstr1 : itsvalue23
                     yetanotherstr2 : itsvalue24
               str2: yetanotherstr1 : itsvalue47
                     yetanotherstr2 : itsvalue48
               str3: yetanotherstr1 : itsvalue71
                     yetanotherstr2 : itsvalue72
               str4: yetanotherstr1 : itsvalue95
                     yetanotherstr2 : itsvalue96
...