C++ 我如何通过其 .second 参数对地图进行排序
声明:本页面是StackOverFlow热门问题的中英对照翻译,遵循CC BY-SA 4.0协议,如果您需要使用它,必须同样遵循CC BY-SA许可,注明原文地址和作者信息,同时你必须将它归于原作者(不是我):StackOverFlow
原文地址: http://stackoverflow.com/questions/2453425/
Warning: these are provided under cc-by-sa 4.0 license. You are free to use/share it, But you must attribute it to the original authors (not me):
StackOverFlow
How can i sort a map by its .second parameter
提问by amitlicht
If i have a stl map from string to int and i want to print all the int values sorted - how can i do that?
如果我有一个从字符串到 int 的 stl 映射,并且我想打印所有已排序的 int 值 - 我该怎么做?
回答by Konrad Rudolph
You cannot sort a map by its values due to the implementation of the map.
由于地图的实施,您无法按地图的值对地图进行排序。
If you want to emit the elements in the map in such a sorted order then you have to first dump the map contents into a vector (say) and sort that vector:
如果您想以这样的排序顺序发出地图中的元素,那么您必须首先将地图内容转储到一个向量中(比如说)并对该向量进行排序:
template <typename T1, typename T2>
struct less_second {
typedef pair<T1, T2> type;
bool operator ()(type const& a, type const& b) const {
return a.second < b.second;
}
};
map<string, int> mymap;
// …
vector<pair<string, int> > mapcopy(mymap.begin(), mymap.end());
sort(mapcopy.begin(), mapcopy.end(), less_second<string, int>());
Or alternatively, just copy the values from the map, leaving the keys, and sort the resulting vector directly.
或者,只需从映射中复制值,保留键,然后直接对结果向量进行排序。
回答by Draco Ater
You can copy all the values into vector and sort it.
您可以将所有值复制到向量中并对其进行排序。
#include <algorithm>
#include <map>
#include <vector>
int get_second( pair<string, int> i ){ return i.second; }
int main(int argc, char* argv){
map<string, int> m;
m["tt"] = 2;
m["rr"] = 1;
m["ee"] = 3;
vector<int> v( m.size() );
transform( m.begin(), m.end(), v.begin(), get_second );
sort( v.begin(), v.end() );
for (int i=0; i<v.size(); i++) cout << v[i] << endl;
}
回答by Janusz Lenar
You cannot do this automatically. std::map
uses first value (nomen omen 'key') to sort content.
您不能自动执行此操作。std::map
使用第一个值(nomen omen 'key')对内容进行排序。
Instead, you can use boost::multi_index_container
.
相反,您可以使用boost::multi_index_container
.
回答by JRL
If you need to do this multiple times, it might be more efficient to keep two separate containers, e.g. your map and a sorted container like set
or multiset
for storing the sorted ints, rather than having to create a container and sort it on the fly. But then you have to keep them synchronized, which could get mucky. You could encapsulate that by wrapping them in a class, or better yet use a boost::multi_index_container
.
如果您需要多次执行此操作,保留两个单独的容器可能更有效,例如您的地图和一个排序的容器,例如set
或multiset
用于存储排序的整数,而不必创建一个容器并对其进行动态排序。但是你必须让它们保持同步,这可能会变得很糟糕。您可以通过将它们包装在一个类中来封装它,或者更好地使用boost::multi_index_container
.
回答by sbi
You cannot sort a map, it's an associativecontainer, not a sequential, and associated containers are sorted by some internal order.
您不能对地图进行排序,它是一个关联容器,而不是一个连续的,并且关联的容器按某种内部顺序进行排序。
If you want to only print the int
values, you could put them into a std::vector
, sort the vector, and print the values.
如果只想打印int
值,可以将它们放入 a std::vector
,对向量进行排序,然后打印值。
回答by dirkgently
Instead of using a vector
, I'd rather just copy them to a set<int>
:
而不是使用 a vector
,我宁愿将它们复制到 a set<int>
:
#include <map>
#include <set>
#include <string>
#include <iostream>
#include <iterator>
using namespace std;
set<int> map2set(map<string, int> const& m) {
set<int> r;
for (map<string, int>::const_iterator b = m.begin(), e = m.end(); b != e; ++b)
r.insert(b->second);
return r;
}
int main() {
map<string, int> m;
m.insert(make_pair("hello", 42));
m.insert(make_pair("world", 24));
set<int> s = map2set(m);
copy(s.begin(), s.end(), ostream_iterator<int>(cout, "\n"));
}