如何按两个值而不是仅按第二个值对向量对进行排序?
How do I sort a vector of pairs by both of the values rather than just the second one?
我想要做的是以第一个值从最低到最大,第二个从最大到最低的方式对向量对进行排序,并且优先于第一个值排序,同时将它们保持在一起。例如,假设我有这个代码:
#include <iostream>
#include <vector>
using namespace std;
int main()
{
pair<int, double> p;
vector<pair<int, double> > vp;
p.first = 2;
p.second = 2.4;
vp.push_back(p);
p.first = 9;
p.second = 3.0;
vp.push_back(p);
p.first = 10;
p.second = 3.1;
vp.push_back(p);
p.first = 1;
p.second = 2.4;
vp.push_back(p);
p.first = 5;
p.second = 3.1;
vp.push_back(p);
}
如果我要通过循环将其打印出来,我希望它不再输出:
2, 2.4
9, 3.0
10, 3.1
1, 2.4
5, 3.1
输出这个
5, 3.1
10, 3.1
9, 3.0
1, 2.4
2, 2.4
现在想象一下,如果这些值不是手动给出的,而是随机的,并且在每次代码为 运行 时循环从 0 到 100(含)之间的随机次数的 for 循环随机化,该对两侧的每个新随机值都存储在向量中(这将使向量的大小为 10。)
如何整理矢量,使其输出的顺序与上述示例相同?
最简单的方法是使用标准函数 std::sort()
和 std::tie()
。
这里有一个演示程序:
#include <iostream>
#include <utility>
#include <vector>
#include <iterator>
#include <algorithm>
int main()
{
std::vector<std::pair<int, double>> v =
{
{ 2, 2.4 },
{ 9, 3.0 },
{ 10, 3.1 },
{ 1, 2.4 },
{ 5, 3.1 }
};
std::sort( std::begin( v ), std::end( v ),
[]( const auto &p1, const auto &p2 )
{
return std::tie( p2.second, p1.first ) < std::tie( p1.second, p2.first );
} );
for (const auto &p : v)
{
std::cout << p.first << ' ' << p.second << '\n';
}
}
程序输出为:
5 3.1
10 3.1
9 3
1 2.4
2 2.4
将std::sort()
与自定义比较器一起使用,例如:
#include <algorithm>
std::sort(vp.begin(), vp.end(),
[](const std::pair<int, double> &p1, const std::pair<int, double> &p2){
if (p1.second > p2.second) return true;
if (p1.second < p2.second) return false;
return p1.first < p2.first;
}
);
输出:
5, 3.1
10, 3.1
9, 3
1, 2.4
2, 2.4
我想要做的是以第一个值从最低到最大,第二个从最大到最低的方式对向量对进行排序,并且优先于第一个值排序,同时将它们保持在一起。例如,假设我有这个代码:
#include <iostream>
#include <vector>
using namespace std;
int main()
{
pair<int, double> p;
vector<pair<int, double> > vp;
p.first = 2;
p.second = 2.4;
vp.push_back(p);
p.first = 9;
p.second = 3.0;
vp.push_back(p);
p.first = 10;
p.second = 3.1;
vp.push_back(p);
p.first = 1;
p.second = 2.4;
vp.push_back(p);
p.first = 5;
p.second = 3.1;
vp.push_back(p);
}
如果我要通过循环将其打印出来,我希望它不再输出:
2, 2.4
9, 3.0
10, 3.1
1, 2.4
5, 3.1
输出这个
5, 3.1
10, 3.1
9, 3.0
1, 2.4
2, 2.4
现在想象一下,如果这些值不是手动给出的,而是随机的,并且在每次代码为 运行 时循环从 0 到 100(含)之间的随机次数的 for 循环随机化,该对两侧的每个新随机值都存储在向量中(这将使向量的大小为 10。)
如何整理矢量,使其输出的顺序与上述示例相同?
最简单的方法是使用标准函数 std::sort()
和 std::tie()
。
这里有一个演示程序:
#include <iostream>
#include <utility>
#include <vector>
#include <iterator>
#include <algorithm>
int main()
{
std::vector<std::pair<int, double>> v =
{
{ 2, 2.4 },
{ 9, 3.0 },
{ 10, 3.1 },
{ 1, 2.4 },
{ 5, 3.1 }
};
std::sort( std::begin( v ), std::end( v ),
[]( const auto &p1, const auto &p2 )
{
return std::tie( p2.second, p1.first ) < std::tie( p1.second, p2.first );
} );
for (const auto &p : v)
{
std::cout << p.first << ' ' << p.second << '\n';
}
}
程序输出为:
5 3.1
10 3.1
9 3
1 2.4
2 2.4
将std::sort()
与自定义比较器一起使用,例如:
#include <algorithm>
std::sort(vp.begin(), vp.end(),
[](const std::pair<int, double> &p1, const std::pair<int, double> &p2){
if (p1.second > p2.second) return true;
if (p1.second < p2.second) return false;
return p1.first < p2.first;
}
);
输出:
5, 3.1
10, 3.1
9, 3
1, 2.4
2, 2.4