Hdoj 1317 XYZZY

来源:互联网 发布:java项目怎么打包上线 编辑:程序博客网 时间:2024/06/08 00:22

题目传送门

  建图后,本题考察1到n这两个点是否联通,以及求最长路判断正环,floyd()判断连通性,spfa判断是否有正环即可。  Talk is cheap.Show coder.
#include<cstdio>#include<cstring>#include<cctype>#include<queue>#include<algorithm>#include<iostream>using namespace std;int dis[110],in[110],val[110];bool maze1[110][110],maze2[110][110];int n;void Floyd(){    for(int i=1;i<=n;i++)        for(int j=1;j<=n;j++)           for(int k=1;k<=n;k++)               maze2[i][j]=(maze2[i][j]||(maze2[i][k]&&maze2[k][j]));}bool spfa(){    queue<int>Q;    Q.push(1);    memset(in,0,sizeof(in));    memset(dis,0,sizeof(dis));    dis[1]=100;    while(!Q.empty())    {        int cur=Q.front();        Q.pop();        in[cur]++;        if(in[cur]>=n)            return maze2[cur][n];        for(int next=1;next<=n;next++)        {            if(maze1[cur][next]&&dis[cur]+val[next]>dis[next]&&dis[cur]+val[next]>0)            {                Q.push(next);                dis[next]=dis[cur]+val[next];            }        }    }    if(dis[n]>0)        return true;    return false;}int main(){    while(~scanf("%d",&n))    {        if(n==-1)break;        memset(maze1,false,sizeof(maze1));        memset(maze2,false,sizeof(maze2));        for(int i=1;i<=n;i++)        {            int num,tmp;            scanf("%d",&val[i]);            scanf("%d",&num);            for(int j=1;j<=num;j++)            {                scanf("%d",&tmp);                maze1[i][tmp]=maze2[i][tmp]=true;            }        }        Floyd();        if(!maze2[1][n])        {            puts("hopeless");        }        else        {            if(spfa())                puts("winnable");            else                puts("hopeless");        }    }    return 0;}
0 0
原创粉丝点击