简体   繁体   English

C++ 将所有元素从向量复制到 map / unordered_map 的最佳方法

[英]C++ best way to copy all elements from vector into map / unordered_map

Using C++, if I want to convert a vector into set or unordered_set container, it can be easily done by:使用 C++,如果我想将vector转换为setunordered_set容器,可以通过以下方式轻松完成:

#include <iostream>
#include <map>
#include <set>
#include <unordered_map>
#include <unordered_set>
#include <vector>
using namespace std;

int main() {
    vector<int> vec {1, 2, 2, 3, 3, 3, 4, 4, 4, 4};

    // pass
    unordered_set<int> uSet(vec.begin(), vec.end());
    // pass
    set<int> s(vec.begin(), vec.end());
    // fail
    unordered_map<int, size_t> uMap(vec.begin(), vec.end());
    // fail
    map<int, size_t> m(vec.begin(), vec.end());

    return 0;
}

However, the same technique doesn't work for map or unordered_map containers.但是,相同的技术不适用于mapunordered_map容器。 I'm wondering if there is a better way to store all the elements from a vector into map / unordered_map container other than:我想知道是否有更好的方法将向量中的所有元素存储到map / unordered_map容器中,而不是:

for (int ele : vec) {
    ++uMap[ele];
}

Also, which copy constructor from https://en.cppreference.com/w/cpp/container/unordered_set/unordered_set is called for the code below:此外,下面的代码调用了https://en.cppreference.com/w/cpp/container/unordered_set/unordered_set的复制构造函数:

set<int> s(vec.begin(), vec.end()); 

And why a similar copy constructor from https://en.cppreference.com/w/cpp/container/unordered_map/unordered_map is not available?为什么来自https://en.cppreference.com/w/cpp/container/unordered_map/unordered_map的类似复制构造函数不可用?

A map entry has two "values", while a vector has only one. map 条目有两个“值”,而向量只有一个。 If you want to insert vector elements into a map, you need to decide which values are going to be the keys and which are going to be the values.如果要将向量元素插入 map,则需要确定哪些值将成为键,哪些值将成为值。 The way of doing that is using a vector of pairs (vector < pair < K, V > >), which can be used to initialize a map as you had already done before.这样做的方法是使用成对的向量(向量 < pair < K, V > >),它可用于初始化 map,就像您之前所做的那样。

Let's look at your set construction.让我们看看你的set结构。

 vector<int> vec {1, 2, 2, 3, 3, 3, 4, 4, 4, 4}; set<int> s(vec.begin(), vec.end());

This succeeds because the value_type of your set is int .这成功了,因为您的setvalue_typeint That's not just convenient terminology.这不仅仅是方便的术语。 A std::set defines a member type called value_type , and I am saying that std::set<int>::value_type is int . std::set定义了一个名为value_type成员类型,我说std::set<int>::value_typeint Since dereferencing vec.begin() gives a value implicitly convertible to int (well, it is int ), this construction succeeds.由于取消引用vec.begin()会给出一个可隐式转换为int的值(嗯,它int ),因此此构造成功。

Moving over to map , there is again a member type called value_type .转到map ,再次有一个名为value_type成员类型 This time, though, value_type is not int , hence your proposed construction fails.但是,这一次value_type不是int ,因此您建议的构造失败。 The value_type of a map is a pair containing the key-value pair. mapvalue_type是包含键值pair的对。 That is, std::map<int, size_t>::value_type is std::pair<int, size_t> .也就是说, std::map<int, size_t>::value_typestd::pair<int, size_t> Since there is no known conversion from int to any flavor of std::pair , your proposed construction fails.由于没有从intstd::pair任何风格的已知转换,因此您建议的构造失败。

If you had instead worked from a vector of pair s, your construction could succeed.如果您改为从pairvector开始工作,那么您的构造可能会成功。

vector<pair<int, size_t>> vecp { {1, 2}, {2, 3}, {3, 3}, {4, 4}, {4, 4} };

map<int, size_t> m(vecp.begin(), vecp.end());

This results in m[1] == 2 , m[2] == 3 , m[3] == 3 , and m[4] == 4 .这导致m[1] == 2m[2] == 3m[3] == 3m[4] == 4 The extra {4,4} is dropped because this is a map , not a multimap .额外的{4,4}被删除,因为这是map ,而不是multimap (It is unspecified whether the first or second {4,4} is dropped, but whichever is dropped is the extra one.) (未指定第一个或第二个{4,4}是否被丢弃,但无论哪个被丢弃都是额外的。)

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

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