[英]how to use a vector of keys to filter values from a map and produce a set using c++ ranges syntax
我是Eric Niebler 的 range-v3 庫的新手,我想解決以下簡單問題:
我有一個std::map
包含以下內容:
std::map<std::string, int> map = {
{"THIS", 1}, {"IS", 2}, {"A", 3}, {"TEST", 4}, {"WITH", 5}, {"MORE", 6}, {"KEYS", 7}
};
我有一個std::vector
包含一組鍵,如下所示:
std::vector<std::string> vec = {
"THIS", "IS", "A", "TEST"
};
如何使用庫(理想情況下使用 pipe 組合語法)從包含向量中的鍵的 map 中過濾掉對,並將結果視圖轉碼為std::set<std::pair<std::string, int>>
. 此外,為了使轉碼有趣,請確保 map 中的值必須是奇數。 在這種情況下,范圍代碼應該:
使用這些鍵:
THIS,IS,A,TEST,
針對這個 map
{A,3},{IS,2},{KEYS,7},{MORE,6},{TEST,4},{THIS,1},{WITH,5},
具有奇數 map 值謂詞 - 產生以下結果作為不同類型的容器std::set
{A,3},{THIS,1},
這應該相對簡單,但我無法弄清楚新語法。 此外,任何關於渴望與懶惰的見解都將有助於我理解。
以下精簡的coliru示例顯示了我正在尋找的內容。
您是否正在尋找這樣的東西:
std::map<std::string, int> map = {{"THIS", 1}, {"IS", 2}, {"A", 3}, {"TEST", 4},
{"WITH", 5}, {"MORE", 6}, {"KEYS", 7}};
std::vector<std::string> keys = {"THIS", "IS", "A", "TEST"};
auto output = map | ranges::views::filter([&](auto &&pair) {
return std::find(keys.begin(), keys.end(), pair.first) != keys.end() && pair.second % 2 == 1;
});
std::set<std::pair<std::string, int>> set(output.begin(), output.end());
for (auto [key, value] : set) std::cout << key << " " << value << std::endl;
在這里,我用向量過濾了 map 並創建了一個range adaptor closure object
。 然后我從 output 創建了一個集合。
關於懶惰,看這段代碼:
std::map<std::string, int> map = {{"THIS", 1}, {"IS", 2}, {"A", 3}, {"TEST", 4},
{"WITH", 5}, {"MORE", 6}, {"KEYS", 7}};
std::vector<std::string> keys = {"THIS", "IS", "A", "TEST"};
auto output = map | ranges::views::filter([&](auto &&pair) {
std::cout << "Seen" << std::endl;
return std::find(keys.begin(), keys.end(), pair.first) != keys.end() && pair.second % 2 == 1;
});
std::cout << "I'm lazy!" << std::endl;
std::set<std::pair<std::string, int>> set(output.begin(), output.end());
for (auto [key, value] : set) std::cout << key << " " << value << std::endl;
我添加了一些印刷品。 output 是:
I'm lazy!
Seen
Seen
Seen
Seen
Seen
Seen
Seen
A 3
THIS 1
這表明在使用output
創建集合之前,不會評估output
。
與遍歷整個map
相比, map
vec
搜索操作是第 logarith
std::set<std::pair<std::string, int>> set;
std::ranges::copy(
vec | std::views::transform([&map](auto& key) { return map.find(key); })
| std::views::filter([&map](auto it) { return it != map.end() &&
it->second % 2 == 1; })
| std::views::transform([](auto it) { return *it; }),
std::inserter(set, set.begin()));
聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.