HDU 3697 Selecting courses

来源:互联网 发布:mac 文件重命名 命令 编辑:程序博客网 时间:2024/06/13 01:56

题意:每隔5分钟选一次课,可以在任意时间点开始,每个时间点最多选一门课,如果选课时间点在这门课的选课时间范围内(开区间)则可以选,求最大的选课数

解题思路:贪心+暴力.将每门课的选课时间按照结束时间排序,并用flag标记每门课,防止同一门课选择两次,然后选课起始时间只需要从0~4这五个时间点开始搜,因为每隔五分钟可以选一次课,假如从0开始,那么选课时间点就是0、5、10、15、20...假如从1开始,那么选课时间点就是1、6、11、17、22...这样每个点都会考虑到,用x数组标记可以选课的时间点,然后从第一门课的起始时间开始一直到结束时间,如果这些时间点里有可以选课的时间,数量就加1,并且还要标记这门课已经选过了,这个选课时间点也不可以再选课了,最后把这n门课还原成都还没有被选的状态,ans不断更新。还要注意的是时间点可以包含左端点但不能包含右端点,例如对左端点0来说,时间点0分11秒是可以选课的,对右端点15来说,15分11秒是不能选的

代码:

#include <iostream>#include <algorithm>#include <string>#include <cstring>#include <cmath>#include <cstdio>using namespace std;struct P{    int st,ed,flag;} p[310];bool cmp(P p1,P p2){    return p1.ed<p2.ed;}int x[1000];int main(){    int n;    while(cin>>n&&n)    {        int r=0;        for(int i=0; i<n; i++)        {            cin>>p[i].st>>p[i].ed;            p[i].flag=1;            r=max(r,p[i].ed);        }        sort(p,p+n,cmp);        int ans=0;        for(int i=0; i<5; i++)        {            memset(x,0,sizeof(x));            int cnt=0;            for(int j=i; j<r; j+=5)x[j]=1;            for(int j=0; j<n; j++)            {                for(int k=p[j].st; k<p[j].ed; k++)                {                    if(x[k]&&p[j].flag)                    {                        cnt++;                        p[j].flag=0;                        x[k]=0;                    }                }            }            ans=max(ans,cnt);            for(int i=0;i<n;i++)            {                p[i].flag=1;            }        }        cout<<ans<<endl;    }    return 0;}


原创粉丝点击