23. 合并 K 个升序链表
代码
class Solution {
public:
ListNode *mergeKLists(vector<ListNode *> &lists) {
auto cmp = [](const ListNode *a, const ListNode *b) {
return a->val > b->val; // 最小堆
};
priority_queue<ListNode*, vector<ListNode*>, decltype(cmp)> pq;
for (auto head: lists)
if (head) pq.push(head);
auto dummy = new ListNode(); // 哨兵节点,作为合并后链表头节点的前一个节点
auto cur = dummy;
while (!pq.empty()) { // 循环直到堆为空
auto node = pq.top(); // 剩余节点中的最小节点
pq.pop();
if (node->next) // 下一个节点不为空
pq.push(node->next); // 下一个节点有可能是最小节点,入堆
cur->next = node; // 合并到新链表中
cur = cur->next; // 准备合并下一个节点
}
return dummy->next; // 哨兵节点的下一个节点就是新链表的头节点
}
};
378. 有序矩阵中第 K 小的元素
代码
class Solution {
public:
int kthSmallest(vector<vector<int>>& matrix, int k) {
struct node{
int x,y,val;
};
auto cmp = [](node a, node b){return a.val > b.val;};
priority_queue<node, vector<node>, decltype(cmp)>q;
int n = matrix.size();
for(int i = 0; i < n; i++){
q.push({i,0,matrix[i][0]});
}
int i = 1;
while(i < k){
node it = q.top();
q.pop();
if(it.y < n - 1) q.push({it.x,it.y + 1, matrix[it.x][it.y + 1]});
i++;
}
return q.top().val;
}
};
719. 找出第 K 小的数对距离
代码
class Solution {
public:
//二分+双指针
int smallestDistancePair(vector<int>& nums, int k) {
sort(nums.begin(),nums.end());
int n = nums.size();
int l = 0, r = 1000010;
while(l < r){
int cnt = 0;//代表这个mid是第几个大数
int mid = (l + r) >> 1;
int i = 0;
for(int j = 0; j < n; j++){
while(i < j && nums[j] - nums[i] > mid)i++;
cnt += j - i;
}
if(cnt < k) l = mid + 1;
else r = mid;
}
return r;
}
};
1508. 子数组和排序后的区间和
代码
class Solution {
public:
//双指针+模拟
const int mod = 1e9 + 7;
int rangeSum(vector<int>& nums, int n, int left, int right) {
vector<int> sum(n + 1,0);
sum[0] = nums[0];
for(int i = 1; i < n; i++) sum[i] = sum[i - 1] + nums[i];
vector<int>tp;
for(int r = 0; r < n; r++){
int l = 0;
while(l <= r){
tp.push_back(l == 0 ? sum[r] : sum[r] - sum[l - 1]);
l++;
}
}
sort(tp.begin(),tp.end());
left--;
right--;
long long ans = 0;
for(;left <= right; left++){
ans = (ans + tp[left]) % mod;
}
return ans;
}
};