您的位置:首页 > 其它

Cleaning Shifts(POJ 2376, 贪心)

2017-11-29 21:27 531 查看
题目链接

       选择开始shift为1的那个cow作为第一个(若没有开始shift为1的print-1),找开始shift小于等于这个cow结束shifit+1,结束shift最大且大于上一个cow的结束shift的那个cow作为第二个cow,ans++(若未找到结束shiift大于上一个cow结束shift的cow,print -1),以此类推,直到最后一个cow或者已能覆盖到第T个shift,若找完最后一个cow后都不能覆盖到最后一个shift,print -1。

       这个题我一开始是想用每个cow开始的时间作为数组下标的,即创建数组a[MAX_T],这样搜索的时候会很方便,在下标小于上一个cow结束shift的范围中寻找即可,不过这样的话时间复杂度为O(T),then,TLE。。。

       所以,只能用a
了。不过这样的话为了搜索方便要先排序,而且感觉增加了逻辑上的难度。排序函数sort()我不太了解,据说是用的快速排序,复杂度为O(N*logN),那么这样的话排序的复杂度是高于后面的for循环的,所以整个程序的复杂度为O(N*logN),N最大为25000,T最大为1000000,按以2为底的话,1000000是25000*log25000的4倍以内吧,感觉差距已然不大了,但是这个算法跑了79ms了,上一个TLE了(时间限制为1000ms,是79ms的十倍以上),是因为循环体的差距较大么,还是说难道我复杂度算错了么,如果哪位童鞋知道为什么,麻烦评论一下,感激不尽。

#include<cstdio>
#include<algorithm>
#include<cstring>

using namespace std;

int N, T;
struct cow{
int begin;
int end;
} a[25005];
typedef struct cow Cow;

bool cmp(Cow b, Cow c){
if(b.begin == c.begin) return b.end>c.end;
return b.begin<c.begin;
}
int main()
{
while(~scanf("%d%d", &N, &T)){
for(int i=0; i<N; i++)
scanf("%d%d", &a[i].begin, &a[i].end);
sort(a, a+N, cmp);
if(a[0].begin != 1) printf("-1\n");
else{
int ans = 1;
int now = a[0].end;
int latest = now;
int i = 1;
while(1){
for(; i<N && a[i].begin<=now+1; i++){
if(a[i].end > latest){
latest = a[i].end;
}
}
if(latest > now){
now = latest;
ans++;
}
else break;
}
if(n
4000
ow == T) printf("%d\n", ans);
else printf("-1\n");
}
}
return 0;
}
内容来自用户分享和网络整理,不保证内容的准确性,如有侵权内容,可联系管理员处理 点击这里给我发消息
标签:  ACM 搜索 poj