11776 - Oh Your Royal Greediness!(最大重叠区间)

Problem F
Oh Your Royal Greediness!

Input: Standard Input

Output: Standard Output

 

Once upon a time there lived a greedy landlord in a not far far away country. The landlord used to employ armed enforcers to ensure tax collection from his subjects. All his subjects were farmers and they depended solely on their crops to pay tax. In any single year, an individual farmer had crops in his field during a single continuous time interval. During this interval, an enforcer from the landlord was present in the farmer's field so that he could make sure to take away most of the produced crops to the landlord's burn. An enforcer could take care of at most one farmer at a time.

 

Now, in a glorious lazy morning, the landlord realized that a lot of his subjects were having intersecting production intervals. As he was determined to take the lion's share of crops from all the farmers, he sat down to determine the minimum number of enforcers he needed to ensure that no farmer remained unguarded while having crops in his field.

 

Oh your royal greediness! Don't you realize he who is greedy is always in want? 

 

Input

There will be multiple test cases in the input file. A test case starts with an integer N (0<=N<=1000), denoting the number of farmers. Each of the following lines contains 2 integers E (0<=S<=E<=31536000), the starting & ending time respectively of the production interval of a farmer. Note that time is given in seconds from the start of the year.

 

The end of input will be denoted by a case with N = -1. This case should not be processed.

 

Output

For each test case, print a line in the format, “Case X: Y”, where X is the case number & Y is the minimum number of enforcers required.

 

Sample Input                                                 Output for Sample Input

4

2 6

8 12

4 9

11 14

2

1 2

2 3

-1

Case 1: 2

Case 2: 2



题意:n个农民,看守每次相同时间只能看一个农民,问最少需要几个看守保证每个农民都能看守到。

思路:今天又学到一个新方法,按点扫描。。每次记录下每个人开始和结束时间,开始的话表示多一人结束的话少一人,这样去扫描这个数组就可以了。

代码:

#include <stdio.h>
#include <string.h>
#include <algorithm>
using namespace std;
#define max(a,b) ((a)>(b)?(a):(b))
const int N = 1005;
int n;
struct E {
	int t, flag;
}e[2 * N];

void init() {
	int start, end;
	for (int i = 0; i < n; i++) {
		scanf("%d%d", &start, &end);
		e[i * 2].t = start; e[i * 2].flag = 1;
		e[i * 2 + 1].t = end; e[i * 2 + 1].flag = -1;
	}
}

bool cmp(E a, E b) {
	if (a.t != b.t)
		return a.t < b.t;
	return a.flag > b.flag;
}

int solve() {
	int ans = 0, num = 0;
	sort(e, e + 2 * n, cmp);
	for (int i = 0; i < 2 * n; i++) {
		num += e[i].flag;
		ans = max(ans, num);
	}
	return ans;
}

int main() {
	int cas = 0;
	while (~scanf("%d", &n) && n != -1) {
		init();
		printf("Case %d: %d\n", ++cas, solve());
	}
	return 0;
}



思路:先排序,然后按右区间选,然后看覆盖到了几个区间,每次维护最大值即可。

代码:

#include <stdio.h>
#include <string.h>
#include <algorithm>
using namespace std;
#define max(a,b) ((a)>(b)?(a):(b))
const int N = 1005;
	
int n;
struct Q {
	int s, e;
} q[N];

void init() {
	for (int i = 0; i < n; i++)
		scanf("%d%d", &q[i].s, &q[i].e);
}

bool cmp(Q a, Q b) {
	return a.e < b.e;
}

int solve() {
	int ans = 0, v = -1;
	sort(q, q + n, cmp);
	for (int i = 0; i < n; i++) {
		if (v == q[i].e) continue;
		v = q[i].e; int count = 1;
		for (int j = i + 1; j < n; j++) {
			if (q[j].s <= v) count++;
		}
		ans = max(count, ans);
	}
	return ans;
}

int main() {
	int cas = 0;
	while (~scanf("%d", &n) && n != -1) {
		init();
		printf("Case %d: %d\n", ++cas, solve());
	}
	return 0;
}


评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值