凌乱的yyy / 线段覆盖
题目背景
快 noip 了,yyy 很紧张!
题目描述
现在各大 oj 上有 \(n\) 个比赛,每个比赛的开始、结束的时间点是知道的。
yyy 认为,参加越多的比赛,noip 就能考的越好(假的)。
所以,他想知道他最多能参加几个比赛。
由于 yyy 是蒟蒻,如果要参加一个比赛必须善始善终,而且不能同时参加 \(2\) 个及以上的比赛。
输入格式
第一行是一个整数 \(n\) ,接下来 \(n\) 行每行是 \(2\) 个整数 \(a_{i},b_{i}\) ( \(a_{i}<b_{i}\) ),表示比赛开始、结束的时间。
输出格式
一个整数最多参加的比赛数目。
样例 #1
样例输入 #1
3
0 2
2 4
1 3
样例输出 #1
2
提示
对于 \(20\%\) 的数据, \(n \le 10\)。
对于 \(50\%\) 的数据, \(n \le 10^3\)。
对于 \(70\%\) 的数据, \(n \le 10^{5}\)。
对于 \(100\%\) 的数据, \(1\le n \le 10^{6}\) , \(0 \le a_{i} < b_{i} \le 10^6\)。
解析
贪心
贪心的策略是先给所有的区间按照右边界排序
其中一定要选择第一个区间
为什么?
现在$ (b_1)<=(b_2)$
那么考虑两种\((a_1)\) 和\((a_2)\)的关系
- \((a_1)>(a_2)\)
那么两个区间如下图
那么选择上面的区间一定是划算的
- 因为没有已经排除第一种情况,所以所有区间的关系如下:
\[(a_1) \leq(a_2) \leq(a_3) \leq(a_4)... \leq(a_n)
\]
图:
如果区间2和区间1不相交,那没有影响
如果相交了,仍然是选第一个
因为如果不选第二个,红色部分的长度是没有影响的
因为它不与任何一个区间相交,区间1的有效部分只剩下灰色部分
而灰色部分又被区间2所包含,成为了第一种情况
所以无论如何,选择第一个总是有利的
选择第一个后,还要标记所以与它相交的区间(不能选了)
代码
#include<bits/stdc++.h>
using namespace std;
struct px{
int a;
int b;
}x[2000000];
bool cmp(px x,px y){
return x.b<y.b;
}
int main(){
int n,sum=1,mi;
scanf("%d",&n);
for(int i=1;i<=n;i++)
{
cin >> x[i].a >> x[i].b;
}
sort(x+1,x+n+1,cmp);
mi=x[1].b;
int j=1;
while(j<=n)
{
j++;
if(x[j].a>=mi)
{
sum++;
mi=x[j].b;
}
}
cout << sum;
return 0;
}
本文来自小默的博客,转载请注明原文链接:https://www.cnblogs.com/momotrace/p/p1803.html