• 出题


    【问题描述】

    出题呢,是要讲究题目背景的的。所以有一个素材库,里面有好多各式各样的题面。但
    是不同的题目审核员对题目长度有着执著的要求,每个审核员要求你的题面长度在他的接受范围内。否则题目审核就会不通过。
    现在有一个题面素材库,里面共有 n 条素材,第 i 条素材长度为 len(i)。有 m 个审核员,
    第 i 个审核员的要求题面长度不小于 L(i),不长于 R(i)。但是所有审核员都会疲劳的,所以每个审核员只会审理一道题。你拿着这 n 道题,请问如何给每道题选择一个审核员,使得最后通过的题目数量尽量多。

    【输入】

    第一行两个整数 n 和 m,表示有 n 条素材和 m 个审核员。
    接下来一行为 n 个用空格隔开的整数,表示 n 条素材的长度。
    接下来 m 行里的第 i 行为两个整数 L(i),R(i),表示第 i 个审核员期望的长度不小于 L(i),
    不大于 R(i)。

    【输出】

    一个整数,表示最多可以通过审核几道题目

    【输入输出样例 1】

    Input
    3 4
    2 5 6
    1 3
    2 3
    1 7
    8 9
    Output
    2

    【数据规模和约定】

    共有 3 条素材,长度分别为 2、5、6。可以把长度为 2 的素材送给第一个审核员,长度为 5的送给第三个审核员,长度为 6 不能送给剩下的任何审核员了。

    30%的数据 1 <= n, m <= 10
    60%的数据 1 <= n, m <= 1000
    100%的数据 1 <= n, m <= 100000,1 <= L(i),R(i),len(i) <= 100000,L(i) <= R(i)。

    【题解】

    这题似乎是个贪心题。。。就是以右端点对区间进行排序,用小根堆维护区间。实现即每个点枚举区间,取最前面可行区间即可。

    #include<iostream>
    #include<cmath>
    #include<cstring>
    #include<cstdio>
    #include<cstdlib>
    #include<algorithm>
    #include<queue>
    #include<vector>
    #define fp(i,a,b) for(int i=a;i<=b;i++)
    #define fq(i,a,b) for(int i=a;i>=b;i--)
    #define il inline
    #define re register
    #define ll long long 
    using namespace std;
    const int N=2e5+5;
    struct Point
    {
        int l,r,type;//type中,0是区间,1是点
        bool operator <(const Point & y) const//第一次打符号重载
        {
          return (l<y.l)||(l==y.l&&type<y.type);//左端点为第一关键字,类型为第二关键字
        }
    }a[N];
    int n,m,ans=0;
    priority_queue<int> q;
    il int gi()
    {
       int x=0;
       short int t=1;
       char ch=getchar();
      while((ch<'0'||ch>'9')&&ch!='-') ch=getchar();
      if(ch=='-') t=-1,ch=getchar();
      while(ch>='0'&&ch<='9') x=x*10+ch-48,ch=getchar();
      return x*t;
    }
    int main()
    {
        freopen("bg.in","r",stdin);
        freopen("bg.out","w",stdout);
        n=gi();m=gi();
        fp(i,1,n)
        {
            int l=gi();
            a[i].l=l;a[i].type=1;
        }
        fp(i,1,m)
        {
            int l=gi(),r=gi();
            a[i+n].l=l;a[i+n].r=r;a[i+n].type=0;
        }
        sort(a+1,a+1+n+m);//排序
        //排序之后,点与点之间按照顺序
        //区间和区间之间按照顺序
        //如果区间的左端点和点相同则按照区间优先
        fp(i,1,n+m)
        {
            if(!a[i].type) q.push(-a[i].r);//是区间,右端点压入优先队列
            else//是点
            {
                int l=a[i].l;
                while(q.size()&&-q.top()<l) q.pop(); //当右侧的端点小于当前的点的位置这个区间就没有用了
                if(q.size()) q.pop(),ans++;//如果此时还有区间,则证明右端点要大于这个点,那么,这个区间就选择这个点
            }
        }
        printf("%d
    ",ans);
        fclose(stdin);
        fclose(stdout);
        return 0;
    }
  • 相关阅读:
    Web前端开发资源集锦
    刮刮卡效果
    html5游戏驴子跳
    Bootstrap3实现的响应式幻灯滑动效果个人作品集/博客网站模板
    40款免费社交图标素材
    移动端的推拉效果导航菜单-支持响应式及其多层菜单
    通过HTML5 Visibility API检测页面活动状态
    HTML5游戏开发引擎Pixi.js新手入门讲解
    滚动触发的翻转式文字引用效果
    11个实用的CSS学习工具
  • 原文地址:https://www.cnblogs.com/yanshannan/p/7413141.html
Copyright © 2020-2023  润新知