【PAT L2-001】最短路计数
给定一个无向带权网络,无负边,无重边和自环,每个顶点有一个正数权值。首先求特定原点s到终点d的最短路的个数;然后求所有最短路中顶点权值a[i]之和最大的那条,输出这条路径。
可用dijkstra算法求出所有最短路,用一个pathNum[u]数组记录从s到u的最短路的个数,查找链path[u]保存了到u为止使顶点权值a[i]之和最大的那条路径,sum[u]保存了这条路径的顶点权值和。
对于提交后的第3个测试点,注意更新新引入顶点u的邻居v的距离值dis[v]时,sum[v]无条件更新为sum[u]+a[v],因为要先满足最短路这个条件,得到的顶点才有意义。最短路更新,则sum要重新计算。
参考了博客 http://blog.csdn.net/tc_to_top/article/details/51427223
#include <cstdio>
#include <cstring>
#include <string>
#include <iostream>
#include <algorithm>
#include <stack>
#include <cmath>
#define RINT(V) scanf("%d", &(V))
#define FREAD() freopen("in.txt", "r", stdin)
#define REP(N) for(int i=0; i<(N); i++)
#define REPE(N) for(int i=1; i<=(N); i++)
#define PINT(N) printf("%d", (N))
#define PSTR(S) printf("%s", S)
#define RSTR(S) scanf("%s", S)
#define pn() printf("\n")
#define pb(V) push_back(V)
#define CLEAR(A, V) memset((A), (V), sizeof(A))
using namespace std;
typedef long long ll;
const int MAX_N = ;
const int INF = 0x3fffffff; int n, m, s, d;
int a[MAX_N]; int V;
int G[MAX_N][MAX_N];//邻接矩阵,无边是INF, 自己到自己是0
int dis[MAX_N];//单源最短路数组
int vis[MAX_N];
int path[MAX_N], pathNum[MAX_N];
int sum[MAX_N]; int shortest(){
int minn = INF;
int rt = -;
for(int v=; v<n; v++){
if(v == s) continue;
if(!vis[v] && dis[v] < minn){
minn = dis[v];
rt = v;
}
}
return rt;
} void dijkstra(){
for(int v=; v<n; v++){
if(G[s][v] != INF && v != s){
dis[v] = G[s][v];//一步直达
path[v] = s;
pathNum[v] = ;
sum[v] = a[s] + a[v];
}
}
path[s] = -;
pathNum[s] = ;
vis[s] = ;
sum[s] = a[s];
dis[s] = ;
while(){
int u = shortest();//select the next vertex
if(u == -) break;//no vertex left
//cout << "choose " << u << endl;
vis[u] = ;
for(int v=; v<n; v++){//update priority
if(vis[v]) continue;//只考虑Tk以外,即最短路尚未确定的点
if(dis[v] > dis[u] + G[u][v]){
pathNum[v] = pathNum[u];
dis[v] = dis[u] + G[u][v];
path[v] = u;//记录前驱
sum[v] = sum[u] + a[v];//更新顶点上的权值和
}else if(dis[v] == dis[u] + G[u][v]){//这部分是关键,同值不同解
//cout << "same " << u << endl;
pathNum[v] += pathNum[u];//|Tv| += |Tu| 这一步是关键
if(sum[v] < sum[u] + a[v]){
sum[v] = sum[u] + a[v];
path[v] = u;
}
}
//cout << "path[" << v << "] = " << path[v] << endl;
}
}
} void init(){
for(int u=; u<n; u++){
for(int v=; v<n; v++){
G[u][v] = INF;
}
G[u][u] = ;
dis[u] = INF;
}
CLEAR(path, -);
CLEAR(pathNum, );
CLEAR(sum, );
CLEAR(vis, );
} int main()
{
FREAD();
scanf("%d%d%d%d", &n, &m, &s, &d);
init();
REP(n) RINT(a[i]);
REP(m){
int u, v, w;
scanf("%d%d%d", &u, &v, &w);
G[u][v] = min(G[u][v], w);//其实没有重边
G[v][u] = G[u][v];//邻接矩阵
} dijkstra();//s为源, d为目的地
printf("%d %d\n", pathNum[d], sum[d]); //输出路径
stack<int> sta;
int cur = d;
sta.push(cur);
while(cur != s){
cur = path[cur];
sta.push(cur);
}
while(sta.size() > ){
printf("%d ", sta.top());
sta.pop();
}
printf("%d", sta.top());
return ;
}
【PAT L2-001】最短路计数的更多相关文章
- 【SPFA】 最短路计数
最短路计数 [问题描述] 给出一个N个顶点M条边的无向无权图,顶点编号为1-N.问从顶点1开始,到其他每个点的最短路有几条. [输入格式] 输入第一行包含2个正整数N,M,为图的顶点数与边数. ...
- P1144 最短路计数
P1144 最短路计数 题目描述 给出一个N个顶点M条边的无向无权图,顶点编号为1-N.问从顶点1开始,到其他每个点的最短路有几条. 输入输出格式 输入格式: 输入第一行包含2个正整数N,M,为图的顶 ...
- 洛谷P1144最短路计数题解
最短路计数 此题还是寻找从1到i点总共有几个最短路且每条边的边长为1,对于这种寻找最短路的个数,我们可以反向搜索,即先用\(SPFA\)预处理出所有点的最短路,然后我们反向记忆化搜索,可以用\(sum ...
- 洛谷P1144 最短路计数(SPFA)
To 洛谷.1144 最短路计数 题目描述 给出一个N个顶点M条边的无向无权图,顶点编号为1-N.问从顶点1开始,到其他每个点的最短路有几条. 输入输出格式 输入格式: 输入第一行包含2个正整数N,M ...
- 2018.11.05 NOIP模拟 规避(最短路计数)
传送门 正难则反. 考虑计算两人相遇的方案数. 先正反跑一遍最短路计数. 然后对于一条在最短路上的边(u,v)(u,v)(u,v),如果(dis(s,u)*2<total&&di ...
- 洛谷 P1144 最短路计数 解题报告
P1144 最短路计数 题目描述 给出一个\(N\)个顶点\(M\)条边的无向无权图,顶点编号为\(1-N\).问从顶点1开始,到其他每个点的最短路有几条. 输入输出格式 输入格式: 第一行包含2个正 ...
- BZOJ1632: [Usaco2007 Feb]Lilypad Pond SPFA+最短路计数
Description 为了让奶牛们娱乐和锻炼,农夫约翰建造了一个美丽的池塘.这个长方形的池子被分成了M行N列个方格(1≤M,N≤30).一些格子是坚固得令人惊讶的莲花,还有一些格子是岩石,其余的只是 ...
- 1491. [NOI2007]社交网络【最短路计数】
Description 在社交网络(socialnetwork)的研究中,我们常常使用图论概念去解释一些社会现象.不妨看这样的一个问题. 在一个社交圈子里有n个人,人与人之间有不同程度的关系.我们将这 ...
- 洛谷P1144 最短路计数 及其引申思考
图论题目练得比较少,发一道spfa的板子题目- 题目:P1144 题目描述 给出一个N个顶点M条边的无向无权图,顶点编号为1-N.问从顶点1开始,到其他每个点的最短路有几条. 输入输出格式 输入格式: ...
随机推荐
- c语言else匹配问题
#include <stdio.h> #include <stdlib.h> //实现 依次输入三个递增的数 然后正确输出 //为什么得不到我们想要的结果呢 这就是else匹配 ...
- Homebrew新一代OS X套件管理工具 高速安装Git
在Mac上安装一些开源程序,除了自己下下载.编译( ./configure && make && make install) 之外,通常最方便的选择就是用套件管理工具來 ...
- Ubuntu中设置静态IP和DNS(转载)
原文地址:http://blog.sina.com.cn/s/blog_669421480102v3bb.html VMware 中使用网络,对虚拟机设置静态IP:在Ubuntu中设置静态IP共两步: ...
- Sass函数--颜色函数--HSL函数
HSL函数简介HSL颜色函数包括哪些具体的函数,所起的作用是什么: hsl($hue,$saturation,$lightness):通过色相(hue).饱和度(saturation)和亮度(ligh ...
- AngularJs练习Demo1
@{ Layout = null; } <!DOCTYPE html> <html> <head> <meta name="viewport&quo ...
- silverlight visifire控件图表制作——silverlight 后台方法画图
1.调用wcf 获取信息 private void svc_GetSingleChartDataCompleted(object sender, GetSingleChartDataCompleted ...
- jQuery和DOM对象
html示例 <!DOCTYPE html> <html lang="zh-CN"> <head> <meta charset=" ...
- Python提取图片的ROI
图像处理经常需要提取图片的ROI,本文使用Python提取图片的ROI. 使用的Module是PIL (Pillow),一个图像处理库,用到的函数为类 Image 中的 crop 方法. 函数原型为: ...
- 更快的方式实现PHP数组去重(转)
概述 使用PHP的array_unique()函数允许你传递一个数组,然后移除重复的值,返回一个拥有唯一值的数组.这个函数大多数情况下都能工作得很好.但是,如果你尝试在一个大的数组里使用array_u ...
- python多进程断点续传分片下载器
python多进程断点续传分片下载器 标签:python 下载器 多进程 因为爬虫要用到下载器,但是直接用urllib下载很慢,所以找了很久终于找到一个让我欣喜的下载器.他能够断点续传分片下载,极大提 ...