HDOJ 1317 - XYZZY dp(SPFA)+dfs判联通..细心..

来源:互联网 发布:书生软件 安卓 编辑:程序博客网 时间:2024/05/31 00:39

                   题意:

                           打游戏..从1出发初始100的血...经过每个点就会加一定的血或者扣一定的血...若血量<=0了..就挂了..问能不能活着到达点N...

                   题解:

                           相当于用SPFA求最远距离了..那么注意的就是出现正环的情况..从环上的点dfs一次看能到到达点N..若可以..直接返回true..否则..继续往下找...

                 

Program:

#include<iostream>  #include<algorithm>  #include<stdio.h>  #include<string.h>  #include<math.h>  #include<queue>  #define MAXN 1205#define MAXM 8000005  #define oo 1000000007  #define ll long long  using namespace std;bool A[105][105],F[105],InQ[105];int C[105],times[105],dp[105];void dfs(int x,int n){      F[x]=true;      for (int i=1;i<=n;i++)        if (!F[i] && A[x][i]) dfs(i,n);}bool judge(int n){      int x,i;      queue<int> Q;       memset(dp,-0x2f,sizeof(dp));      memset(times,0,sizeof(times));      memset(InQ,false,sizeof(InQ));      Q.push(1),dp[1]=100;      while (!Q.empty())      {              x=Q.front(),Q.pop();              times[x]++,InQ[x]=false;              if (times[x]>n)               {                     memset(F,false,sizeof(F)),dfs(x,n);                     if (F[n]) return true;                     continue;                                   }              for (i=1;i<=n;i++)                 if (A[x][i] && dp[x]+C[i]>0 && dp[i]<dp[x]+C[i])                 {                         dp[i]=dp[x]+C[i];                         if (!InQ[i]) InQ[i]=true,Q.push(i);                 }      }      return dp[n]>0;}int main() {                 int n,s,e,i,x,m;       while (~scanf("%d",&n) && n>=0)      {                 memset(A,false,sizeof(A));               for (i=1;i<=n;i++)               {                      scanf("%d%d",&C[i],&m);                      while (m--) scanf("%d",&x),A[i][x]=true;               }               if (judge(n)) printf("winnable\n");                       else  printf("hopeless\n");      }      return 0;}