区间覆盖(贪心算法)

问题描述
数轴上有 n (1<=n<=25000)个闭区间 [ai, bi],选择尽量少的区间覆盖一条指定线段 [1, t]( 1<=t<=1,000,000)。
覆盖整点,即(1,2)+(3,4)可以覆盖(1,4)。
不可能办到输出-1
Input
第一行:N和T
第二行至N+1行: 每一行一个闭区间。
Output
选择的区间的数目,不可能办到输出-1
Example

Input

3 10
1 7
3 6
6 10

Output

2

问题分析
这道题输入数据很多,请用scanf而不是cin(scanf比cin快一丢丢)。注意题目中的要求:覆盖整点,即(1,2)+(3,4)可以覆盖(1,4)。题目解法是使用贪心算法:预处理:[s, t] 之外的部分切掉,相互包含:不考虑小区间。按 a 从小到大排序,区间 1 的起点不是 s,无解;否则选择起点在 s 的最长区间。选择区间 [ai, bi] 后的起点应设置为 bi,并切掉 bi 之前的部分。
其实区间覆盖和区间选点有异曲同工之妙,区间+贪心。下面是区间选点的连接,大家可以做一下类比学习:区间选点https://blog.csdn.net/YingMila/article/details/104781398
最后不得不说一句贪心大法好!

#include<stdio.h>
#include<algorithm>
using namespace std;
struct TT
{
	int x,y;
};
bool cmp(TT a,TT b)
{
	return a.x<b.x; 
} 
int main()
{
	int n,ans=0,T,S=1,a0=0,S1=1;
	TT a[25005];
	scanf("%d%d",&n,&T);
	for(int i=0;i<n;i++)
		scanf("%d%d",&a[i].x,&a[i].y);
	sort(a,a+n,cmp);
	while(S<=T)
	{
		while(a0<n && a[a0].x<=S)
		{
			if(S1<a[a0].y+1)
				S1=a[a0].y+1;
			a0++;
		}
		if(S==S1)
		{
			ans=-1;
			break;
		}
		else ans++;
		S=S1;
	}
	printf("%d",ans);
	return 0;
}
发布了19 篇原创文章 · 获赞 0 · 访问量 512

猜你喜欢

转载自blog.csdn.net/YingMila/article/details/104782803