码迷,mamicode.com
首页 > 其他好文 > 详细

ZOJ 3811 Untrusted Patrol

时间:2014-09-12 20:40:04      阅读:220      评论:0      收藏:0      [点我收藏+]

标签:style   blog   http   color   io   os   ar   for   art   

题目链接:http://acm.zju.edu.cn/onlinejudge/showProblem.do?problemCode=3811

解题报告:一个无向图上有n个点和m条边,其中有k个点上安装了传感器,当有人第一次从安装了传感器的点上经过时,在控制室就会收到一个信号,现在保安制定 了一条路线目的是要将所有的点都巡逻一遍,然后在控制室收到了 L 次信号,按顺序给出收到信号的点,问这条路线是否是有可能的?

路线的不可能的情况比如收到信号的点的顺序是123,但是在无向图上要到达2这个点必定先经过3,那么这种情况就是不可能的,因为要经过2之前必定经过3,所以2之前一定会有个3.这题的思路是这样的,用dfs从第一个点开始搜,当当前点的下一个点是没有传感器的可以直接走,如果有传感器的而且刚好是路线上的下一个点,也是直接走,如果是有传感器但又不是路线上的下一个点,则先把这个点放入到一个集合里面去,当所有能走的点都走完了,再在这个集合里面找路线上的下一个点是不是在这个集合里面,最后当集合空了的时候就可以退出了,而且每次走完点之后都要标记掉。另外两个重要的就是首先要判断L 是不是等于k,因为要走完所有的点,当L小于K时,走K-L 的这些点的时候肯定会发出信号,但这些信号又不是路线上的,所以不符合。另一个是要判断这个无向图是不是个连通图,这个简单,如果不是连通图必定会有走不到的点。

bubuko.com,布布扣
  1 #include<cstdio>
  2 #include<cstring>
  3 #include<iostream>
  4 #include<algorithm>
  5 #include<vector>
  6 using namespace std;
  7 const int maxn = 100005;
  8 vector<int> vet[maxn];
  9 int flag[maxn];
 10 int T,n,m,k,l,L[maxn],cizi[maxn],visit[maxn],is[maxn],num;
 11 void find(int p,int* is)
 12 {
 13     if(is[p] == 1) return ;
 14     num++;
 15     is[p] = 1;
 16     for(int i = 0;i < vet[p].size();++i)
 17     find(vet[p][i],is);
 18 }        
 19          
 20 int is_connect(int n)   //判断是否是连通图 
 21 {
 22     num = 0;
 23     memset(is,0,sizeof(is));
 24     find(1,is);
 25     return num == n;
 26 }
 27 void dfs(int s,int* visit,int& p)
 28 {
 29     if(visit[s]) return ;
 30     visit[s] = 1;
 31     if(flag[s]) p++;
 32     for(int i = 0;i < vet[s].size();++i)
 33     {
 34         int nx = vet[s][i];
 35         if(flag[nx] && L[p+1] != nx)   //下一个点是有传感器的,但不是当前位置上的下一个点,则加入集合 
 36         cizi[nx] = 1;
 37         else dfs(nx,visit,p);
 38     }
 39 }
 40 
 41 int main()
 42 {
 43     
 44     scanf("%d",&T);
 45     while(T--)
 46     {
 47         scanf("%d%d%d",&n,&m,&k);
 48         int a,b;
 49         memset(flag,0,sizeof(flag));  //flag[i] = 1表示i点有传感器 
 50         for(int i = 1;i <= k;++i)
 51         {
 52             scanf("%d",&a);
 53             flag[a] = 1;
 54         }
 55         for(int i = 1;i <= n;++i)
 56         vet[i].clear();
 57         for(int i = 1; i<= m;++i)
 58         {
 59             scanf("%d%d",&a,&b);
 60             vet[a].push_back(b);
 61             vet[b].push_back(a);
 62         }
 63         scanf("%d",&l);
 64         for(int i = 1;i <= l;++i)
 65         scanf("%d",&L[i]);
 66         if(l != k || (!is_connect(n)))  //l < k或者不是连通图 
 67         {
 68         //    if(!is_connect(n)) puts("不是连通图"); 
 69             puts("No");
 70             continue;
 71         }
 72         int num_cizi = 1;
 73         memset(cizi,0,sizeof(cizi));  //把集合清空
 74         memset(visit,0,sizeof(visit));
 75         cizi[L[1]] = 1;   //路径上的第一个点加入集合
 76         int s = L[1],p = 0;   //当前走到的路径上的指针 
 77         while(p < l && cizi[s])
 78         {
 79             dfs(s,visit,p);
 80     //        printf("p = %d\n",p);
 81             if(cizi[L[p+1]] == 1)
 82             s = L[p+1];
 83             else break;
 84         }
 85         printf(p == l? "Yes\n":"No\n");
 86     }
 87     return 0;
 88 }
 89 /*
 90 44
 91 6 6 6
 92 1 2 3 4 5 6
 93 1 6
 94 6 3
 95 6 2
 96 2 3
 97 2 5
 98 3 4
 99 6
100 1 6 2 5 3 4
101 */
View Code

 

ZOJ 3811 Untrusted Patrol

标签:style   blog   http   color   io   os   ar   for   art   

原文地址:http://www.cnblogs.com/xiaxiaosheng/p/3969013.html

(0)
(0)
   
举报
评论 一句话评论(0
登录后才能评论!
© 2014 mamicode.com 版权所有  联系我们:gaon5@hotmail.com
迷上了代码!