题目来源
题目描述
题目解析
贪心
本题是要求排序,但是排序有两个维度。看到这种题目我们一定要先确定一个维度,然后再按照另一个维度排
问题是,是先按h排序呢,还先按照k排序呢?
一个人的k值实际上与身高更矮的人的位置无关,所以如果身高比他更高的人已经排好队了,这个人加入当前队列的位置就可以根据k值确定了。因此,身高较高的人应该先加入,我们先对队列按身高降序排序。此外,对于相同身高的人,k值较小的人位置在前,优先加入。
所以策略:先按照h从高到低排序,如果h一样,则按照k从小到大排列,这样就得到了一个方便后面插入的队列
- before: [[7,0] [4,4] [7,1] [5,0] [6,1] [5,2]]
- after : [[7 0] [7 1] [6 1] [5 0] [5 2] [4 4]]
问题是怎么插入呢?
- 比如现在遍历到了[6 1], k = 1, 那么就插入到 index = 1 的位置
- 变成:[[7 0] [6 1] [7 1] [5 0] [5 2] [4 4]]
举个例子:
原始输入:
[[7,0] [4,4] [7,1] [5,0] [6,1] [5,2]]
sort处理:
[[7 0] [7 1] [6 1] [5 0] [5 2] [4 4]]
遍历people:
===== i=0
↓:p[0] 应该在index=0的位置
[[7 0] [7 1] [6 1] [5 0] [5 2] [4 4]]
[[7 0] [7 1] [6 1] [5 0] [5 2] [4 4]] ok
===== i=1
↓:p[1]应该在index=1的位置
[[7 0] [7 1] [6 1] [5 0] [5 2] [4 4]]
[[7 0] [7 1] [6 1] [5 0] [5 2] [4 4]] ok
===== i=2
↓:p[2]应该在index=1的位置
[[7 0] [7 1] [6 1] [5 0] [5 2] [4 4]]
[[7 0] [6 1] [7 1] [5 0] [5 2] [4 4]] ok
===== i=3
↓:p[3]应该在index=0的位置
[[7 0] [6 1] [7 1] [5 0] [5 2] [4 4]]
[[5 0] [7 0] [6 1] [7 1] [5 2] [4 4]] ok
===== i=4
↓:p[4]应该在index=2的位置
[[5 0] [7 0] [6 1] [7 1] [5 2] [4 4]]
[[5 0] [7 0] [5 2] [6 1] [7 1] [4 4]] ok
===== i=5
↓:p[5]应该在index=4的位置
[[5 0] [7 0] [5 2] [6 1] [7 1] [4 4]]
[[5 0] [7 0] [5 2] [6 1] [4 4] [7 1]] ok
最终结果:
[[5 0] [7 0] [5 2] [6 1] [4 4] [7 1]]
核心:高个子站好,矮个子插入
class Solution {
public:
vector<vector<int>> reconstructQueue(vector<vector<int>>& people) {
sort(people.begin(), people.end(), [](const vector<int> &a, const vector<int> &b){
if(a[0] > b[0]) return true;
if(a[0] == b[0] && a[1] < b[1]){
return true;
}
return false;
});
list<vector<int>> que; // list底层是链表实现,插入效率比vector高的多
for (int i = 0; i < people.size(); ++i) {
int pos = people[i][1]; // 插入到下标为position的位置
auto it = que.begin();
while (pos --){ // 寻找在插入位置
it++;
}
que.insert(it, people[i]);
}
return vector<vector<int>>(que.begin(), que.end());
}
};