Codeforces Round #390 (Div. 2)D Fedor and coupons

題目大意:

       給你n個區間,求k個區間的最大並區間長度。

題目解法:

      貪心,不斷想優先隊列中保存內容,保證每次隊列頂端的右值最大,不斷修正左區間。最後按照最優的左端點和右端點,尋找答案就行。

代碼:

#include "iostream"
#include "cstdio"
#include "math.h"
#include "algorithm"
#include "string"
#include "string.h"
#include "vector"
#include "map"
#include "queue"
using namespace std;
int n, k;
struct Node {
	int left, right, id;
	friend bool operator <(Node a, Node b) {
		return a.right > b.right;
	}
}node[300010];
bool cmp(Node a, Node b) {
	if (a.left == b.left)
		return a.right > b.right;
	return a.left < b.left;
}
int main() {
	scanf("%d %d", &n, &k);
	for (int i = 1;i <= n;i++) {
		scanf("%d %d", &node[i].left, &node[i].right);
		node[i].id = i;
	}
	int maxnum = 0, ansleft, ansright;
	sort(node + 1, node + n + 1, cmp);
	priority_queue<Node>que;
	for (int i = 1;i <= n;i++) {
		int left = node[i].left;
		que.push(node[i]);
		if (que.size() > k)
			que.pop();
		int right = que.top().right;
		if (que.size() == k&&right - left + 1 > maxnum) {
			maxnum = right - left + 1;
			ansleft = left;
			ansright = right;
		}
	}
	printf("%d\n", maxnum);
	if (maxnum == 0) {
		for (int i = 1;i <= k;i++) {
			printf("%d ", i);
		}
	}
	else {
		for (int i = 1, j = 0;i <= n&&j < k;i++) {
			if (node[i].left <= ansleft&&node[i].right >= ansright) {
				printf("%d ", node[i].id);
				j++;
			}
		}
	}
	return 0;
}

發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章