您的位置:首页 > 其它

2017.9.29 road 失败总结

2017-09-29 18:41 162 查看
首先要明确:多源最短路不只有floyd,还有n遍单源最短路

而且有时比floyd快。

所以可以用n遍spfa求所有点的单源最短路

期望复杂度n*(n*2)

然后对于每个单源最短路,求出经过每条边的次数(这里指最短路长度相同,经过点不同的边)

然后从源点往下,求不统计相同最短路情况,走到每一条边的至少经过次数

然后对于每一条边,同长的次数*一次的次数就是它经过的次数、

码:

#include<iostream>
#include<cstdio>
#include<cstring>
using namespace std;
int tot,zhong[500005],v[500005],hou[500005],xia[10005],d[10005],cnt,n,m,a,b,c,i,s;
bool vis[10005];
void jia(int a,int b,int c)
{
++tot,zhong[tot]=b,v[tot]=c,hou[tot]=xia[a],xia[a]=tot;
}
struct dian
{
int id,v;
}dui[100005];
void ins()
{
int o=cnt;
bool f=0;
while(o>1&&!f)
{
if(dui[o/2].v<dui[o].v)
{
swap(dui[o/2],dui[o]);
}else f=1;
o=o/2;
}
}
void del()
{
dui[1]=dui[cnt];
cnt--;
int o=1;
int mb=o;
bool f=0;
while(o<=cnt&&!f)
{
if(o*2<=cnt&&dui[o*2].v<dui[o].v)
mb=o*2;
if(o*2+1<=cnt&&dui[o*2+1].v<dui[o].v&&dui[o*2+1].v<dui[o*2].v)
mb=o*2+1;
if(o==mb)f=1;
else
{
swap(dui[o],dui[mb]);
o=mb;
}
}
}
void dij(int s)
{
dian o;
int i;
d[s]=0;
dui[++cnt].id=s;
dui[cnt].v=0;
while(cnt)
{
o=dui[1];
del();
if(vis[o.id])continue;
vis[o.id]=1;//cout<<cnt<<endl;
cout<<o.id<<endl;
for(i=xia[o.id];i!=-1;i=hou[i])
{
int nd=zhong[i];
if(d[nd]>o.v+v[i])
{
d[nd]=o.v+v[i];
dui[++cnt].id=nd;
dui[cnt].v=d[nd];
ins();
}
}
}
}
int main()
{
memset(xia,-1,sizeof(xia));
scanf("%d%d%d",&n,&m,&s);
for(i=1;i<=n;i++)
d[i]=2147483647;
for(i=1;i<=m;i++)
{scanf("%d%d%d",&a,&b,&c);
jia(a,b,c);
}
dij(s);
for(i=1;i<=n;i++)
printf("%d ",d[i]);
}
内容来自用户分享和网络整理,不保证内容的准确性,如有侵权内容,可联系管理员处理 点击这里给我发消息
标签: