zoukankan      html  css  js  c++  java
  • 区间覆盖问题(贪心)

    题目链接:http://acm.hust.edu.cn/vjudge/contest/view.action?cid=85904#problem/D
    题意:

           给出一些区间[Li,Ri],请你找到这些区间的一个子集,使得子集里的区间完全覆盖[0,M].

           输入:首行输入案例数。换行后第三行包含一个数M(1<=M<=50000),其接下来每行包含一对数Li和Ri(|Li|<=50000,|Ri|<=50000),最后以"0 0"结束,案例与案例之间用换行分隔。

           输出:输出一个整数k,表示最少需要多少个区间覆盖[0,M],并在接下来的k行将这些区间按照左边数从小到大的顺序排列出。如果无解,则输出"0",不带引号。不同案例的解使用换行符间隔。

    案例:

             Sample Input          

         2
         1
         -1 0
         -5 -3
         2 5
         0 0
     
         1
         -1 0
         0 1
         0 0

           Sample Output

         0
     
         1
         0 1

    分析:

             将所给覆盖区间从小到大排序,先比较起点,若一致则比较终点。被覆盖区间的起点是0,那么找出所有区间起点小于0中的最合适的区间。要求用尽量少的区间覆盖,所以选择右端点更大的区间,它包含区间长度更长,更易覆盖。如果在所有覆盖区间中找到了解,但右端点小于M,则把找到的覆盖区间的右端点定为新的覆盖区间的起点。


    源代码:

     1 #include<cstdio>
     2 #include<algorithm>
     3 #include<cstring>
     4 using namespace std;
     5 int M;
     6 struct qj//结构体
     7 {
     8     int l;
     9     int r;
    10 }a[100010],b[100010];//对象
    11 int cmp(const qj &a,const qj &b)//排序
    12 {
    13     if(a.l!=b.l) return a.l<b.l;
    14     else return a.r>b.r;
    15 }
    16 int main()
    17 {
    18     int T,x,y,j,max,ans,t;
    19     scanf("%d",&T);//案例数
    20     while(T--)
    21     {    
    22         memset(a,0,sizeof(a));
    23         memset(b,0,sizeof(b));
    24         int i=0,ant=0,min=0;//ant为覆盖区间数,min为覆盖区间左极限(起点)
    25         scanf("%d",&M);//被覆盖区间[0,M]
    26         while(scanf("%d%d",&x,&y))//给定分区间
    27         {
    28             if(!x&&!y) break;
    29             a[i].l=x;
    30             a[i].r=y;
    31             i++;
    32         }
    33         max=0;//覆盖区间右极限(终点)
    34         sort(a,a+i,cmp);//排序
    35         while(1)
    36         {
    37             if(min>=M) break;//覆盖区间超过被覆盖区间
    38             ans=0;
    39             for(j=0;j<i;j++)//找寻覆盖区间
    40             {
    41                 if(a[j].l<=min)
    42                 {
    43                     if(a[j].r>max)
    44                     {
    45                         t=j;//标记区间
    46                         max=a[j].r;
    47                         ans=1;
    48                     }
    49                 }
    50             }
    51             if(ans)//判断覆盖区间是否满足条件
    52             {
    53                 min=max;//更改起点
    54                 b[ant]=a[t];
    55                 ant++;
    56             }
    57             else break;
    58         }
    59         if(ans)//输出控制
    60         {
    61             printf("%d
    ",ant);
    62             for(i=0;i<ant;i++)
    63                 printf("%d %d
    ",b[i].l,b[i].r);
    64         }
    65         else
    66             printf("0
    ");
    67         if(T) printf("
    ");
    68     }
    69     return 0;
    70 }
  • 相关阅读:
    SaltStack入门到精通第一篇:安装SaltStack
    saltstack 基础入门文档
    【基础】centos 6.X 下修改图形界面为命令行界面(单用户救援模式)
    成都达内推荐PHP书籍【update 2017.1.10】
    高性能Mysql主从架构的复制原理及配置详解
    MySQL数据库的初始化mysql_install_db 【基础巩固】
    linux rsync配置文件参数详解
    实时跟踪log变化的工具Apachetop
    实时观察Apache访问情况的工具Apachetop
    apachetop 实时监测web服务器运行状况
  • 原文地址:https://www.cnblogs.com/huaszjh/p/4707234.html
Copyright © 2011-2022 走看看