题目大意:原题链接

给你一张图,初始你在房间1,初始生命值为100,进入每个房间会加上那个房间的生命(可能为负),问是否能到达房间n。(要求进入每个房间后生命值都大于0)

解题思路:

解法一:Floyd+Bellman

1.Floyd先判断图是否连通,不连通则直接失败

2.Bellman Ford然后跑最长路,判断是否有正环或者有正通路

#include<cstdio>
#include<cstring>
using namespace std;
int n,val[],d[];
bool graph[][],link[][];
int main()
{
int i,j,k,cnt,id;
while(scanf("%d",&n),n!=-){
memset(d,-,sizeof(d));
memset(val,,sizeof(val));
memset(link,false,sizeof(link));
memset(graph,false,sizeof(graph));
for(i=;i<=n;i++){
scanf("%d%d",&val[i],&cnt);
while(cnt--){
scanf("%d",&id);
graph[i][id]=true;
link[i][id]=true;//用于判断任意两点间的连通性
}
}
//Floyd判断连通性
for(k=;k<=n;k++){
for(i=;i<=n;i++){
for(j=;j<=n;j++){
if(link[i][k]&&link[k][j])
link[i][j]=true;
}
}
}
if(!link[][n]){
printf("hopeless\n");
continue;
}//必须加上这个
link[n][n]=true;
//Bellman-ford求最长路径
d[]=;
for(k=;k<=n;k++){//遍历每一个节点
bool sign=true;
for(i=;i<=n;i++){//遍历每一条边
for(j=;j<=n;j++){//j,n必须是连通的,并且前一个点d[i]为正
if(graph[i][j]&&link[j][n]&&d[j]<d[i]+val[j]&&d[i]>){
d[j]=d[i]+val[j];
sign=false;
}
}
}//如果d[j]已经不能更新了,说明最长路已经查找完毕,即不存在正环,退出循环
if(sign) break;
}
if(k>n||d[n]>) printf("winnable\n");//有正环或者有正通路
else printf("hopeless\n");
}
}

解法二:Spfa+Floyd

1.Spfa先判正环+跑最长路,以及判断是否存在正通路

2.若d[n]<=0,则Floyd然后根据存在正环以及是否连通起点和终点判断是否会成功到达n点

#include<cstdio>
#include<cstring>
#include<queue>
#define inf 0x3f3f3f3f
using namespace std;
int n,p,num[];//num[u]表示u入队次数
int val[],d[];
bool in[],link[][];
queue<int> que;
bool Spfa_floyd(int u)
{
for(int i=;i<=n;i++){
d[i]=-inf;
in[i]=,num[i]=;
}
while(!que.empty()) que.pop();//que定义为全局变量就得清空队列
que.push(u);
in[u]=true;
num[u]=,d[u]=;
while(!que.empty()){
u=que.front();
que.pop();
in[u]=false;
if(num[u]>n){
p=u;
break;//Spfa某节点入队次数大于n则有正环
}
for(int v=;v<=n;v++){
if(link[u][v]&&d[u]+val[v]>&&d[u]+val[v]>d[v]){
d[v]=d[u]+val[v];//最长路
if(!in[v]){
que.push(v);
in[v]=true;
num[v]++;
}
}
}
}
if(d[n]>) return true;
else{
for(int k=;k<=n;k++)
for(int i=;i<=n;i++)
for(int j=;j<=n;j++)
if(link[i][k]&&link[k][j])
link[i][j]=true;
if(num[p]>n&&link[][p]&&link[p][n])
return true;//如果存在正环,并且连接起点和终点
return false;
}
} int main()
{
while(scanf("%d",&n),n!=-){
memset(link,,sizeof(link));
memset(val,,sizeof(val));
for(int i=;i<=n;i++){
int cnt,id;
scanf("%d%d",&val[i],&cnt);
for(int j=;j<=cnt;j++){
scanf("%d",&id);
link[i][id]=true;
}
}
if(Spfa_floyd()) puts("winnable");
else puts("hopeless");
}
}

PKU 1932 XYZZY(Floyd+Bellman||Spfa+Floyd)的更多相关文章

  1. POJ 1932 XYZZY (ZOJ 1935)SPFA+floyd

    http://poj.org/problem?id=1932 http://acm.zju.edu.cn/onlinejudge/showProblem.do?problemCode=1935 题目大 ...

  2. poj 1932 XYZZY(spfa最长路+判断正环+floyd求传递闭包)

    XYZZY Time Limit: 1000MS   Memory Limit: 30000K Total Submissions: 4154   Accepted: 1185 Description ...

  3. 最短路问题(Bellman/Dijkstra/Floyd)

    最短路问题(Bellman/Dijkstra/Floyd) 寒假了,继续学习停滞了许久的算法.接着从图论开始看起,之前觉得超级难的最短路问题,经过两天的苦读,终于算是有所收获.把自己的理解记录下来,可 ...

  4. HDU 2992 Hotel booking(BFS+DFS 或者 SPFA+Floyd)

    点我看题目 题意 : 一个司机要从1点到达n点,1点到n点中有一些点有宾馆,司机的最长开车时间不能超过10小时,所以要在10小时之内找到宾馆休息,但是为了尽快的走到n点,问最少可以经过几个宾馆. 思路 ...

  5. 四大算法解决最短路径问题(Dijkstra+Bellman-ford+SPFA+Floyd)

    什么是最短路径问题? 简单来讲,就是用于计算一个节点到其他所有节点的最短路径. 单源最短路算法:已知起点,求到达其他点的最短路径. 常用算法:Dijkstra算法.Bellman-ford算法.SPF ...

  6. 最短路算法详解(Dijkstra/SPFA/Floyd)

    新的整理版本版的地址见我新博客 http://www.hrwhisper.me/?p=1952 一.Dijkstra Dijkstra单源最短路算法,即计算从起点出发到每个点的最短路.所以Dijkst ...

  7. poj 1932 XYZZY (最短路径)

    XYZZY Time Limit: 1000MS   Memory Limit: 30000K Total Submissions: 3105   Accepted: 887 Description ...

  8. 一个人的旅行(floyd+dijskra+SPFA+Bellman)

    一个人的旅行 Time Limit: 1000/1000 MS (Java/Others)    Memory Limit: 32768/32768 K (Java/Others)Total Subm ...

  9. 最短路知识点总结(Dijkstra,Floyd,SPFA,Bellman-Ford)

    Dijkstra算法: 解决的问题: 带权重的有向图上单源最短路径问题.且权重都为非负值.如果采用的实现方法合适,Dijkstra运行时间要低于Bellman-Ford算法. 思路: 如果存在一条从i ...

随机推荐

  1. css 动画

    CSS3动画相关的几个属性是:transition, transform, animation:我分别理解为过渡,变换,动画.虽意义相近,但具体角色不一.就像是SHE组合,虽然都是三个女生,都唱同一首 ...

  2. 我在Facebook学到的10个经验

    1.坚持你的远景,但要对细节灵活. 作为一个领导者,你需要依赖你自己的远景(至少在你负责的业务领域内)而那些和你一起或为你工作的人将依赖你的远见.什么是远景?就是对最终状态的一种描述.是你需要你的团队 ...

  3. angularJs 多文件动态上传(删除其中一个文件的时候,要么file没被删除,要么删除了之后,点击事件失效)

    <div cacModule.controller('CacScriptEditCtrl', CacScriptEditCtrl); CacScriptEditCtrl.$inject = [' ...

  4. Redis分布式锁,基于StringRedisTemplate和基于Lettuce实现setNx

    使用redis分布式锁,来确保多个服务对共享数据操作的唯一性一般来说有StringRedisTemplate和RedisTemplate两种redis操作模板. 根据key-value的类型决定使用哪 ...

  5. 打印系统所有的PID

    #!/usr/bin/env python #-*- coding:utf-8 -*- ''' 打印系统所有的PID ''' import os def get_all_pid(): for pid ...

  6. 从远程(包括ftp,http等协议)地址获取文件流信息

    URL url = new URL("ftp://172.18.251.155:8010/recordsImg/2019-01-28/000008_1548649813267.jpg&quo ...

  7. Jfinal报错sql injection violation, multi-statement not allow

    Jfinal报错: com.jfinal.plugin.activerecord.ActiveRecordException: java.sql.SQLException: sql injection ...

  8. Hibernate传递list参数的例子

    public Map<String, String> getAllFeedBack(Object[] obj){ Map<String, String> map = new H ...

  9. vue-router scrollBehavior无效的问题

    在使用vue做单页面应用开发时候 使用vue-router作为路由控制器  在使用过程中发现每个页面打开都在原来的位置 不能返回到页面顶部位置 ,然后查看api文档 滚动行为  发现如下代码: con ...

  10. linux 定时备份mysql数据库

    首先要先搞清楚两个概念: ①.mysqldump,mysqldump是mysql的逻辑备份工具,它不是linux的命令,工作原理类似产生一些列sql语句,对数据库进行指定的逻辑备份. 最简洁的形式是: ...