洛谷P1144-最短路计算【日常最短路,日常图论,SPFA】

题目

一个无向图,求点1到每个点的最短路的路径数量

输入

5 7(5个点,7条边)
1 2(表示1到2有边)
1 3
2 4
3 4
2 3
4 5
4 5

输出

(答案mod100003)
1
1
1
2
4


解题思路

注意这是无向图,然后请看数据范围

对于20%的数据,N ≤ 100;
对于60%的数据,N ≤ 1000;
对于100%的数据,N<=1000000,M<=2000000。

这是个稀疏图,数据大,所以我们用SPFA法(其实bfs也可以过)。


代码

#include
using namespace std;
struct woc{
    int next,x,y;
};//邻接表
woc a[2000001];
int xx,yy,n,m,k,state[1000001],ls[1000001],t,head,tail,f[1000001],s[1000001];
bool v[1000001];
int main()
{
    scanf("%d%d",&n,&m);
    state[1]=1;
    int u=0;
    for (int i=1;i<=m;i++)
    {
        scanf("%d%d",&xx,&yy);
        a[++u].next=ls[xx];
        a[u].x=xx;
        a[u].y=yy;
        ls[xx]=u;
        a[++u].next=ls[yy];
        a[u].x=yy;
        a[u].y=xx;
        ls[yy]=u;//无向图
    }
    for (int i=1;i<=n;i++) f[i]=2147483647;//初始化
    head=0;
    tail=1;
    state[1]=1;
    v[state[1]]=true;
    f[1]=0; 
    s[1]=1;//开始处理
    while (head!=tail)
    {
        head++;
        head=(head-1)%n+1;
        t=ls[state[head]];
        while (t!=0)
        {
            if (f[a[t].x]+1//继承上一个点
                f[a[t].y]=f[a[t].x]+1;
                if (!v[a[t].y])
                {
                    tail++;
                    tail=(tail-1)%n+1;
                    state[tail]=a[t].y;
                    v[a[t].y]=true;
                }
            }
            else if(f[a[t].x]+1==f[a[t].y])
            {
                s[a[t].y]=(s[a[t].y]+s[a[t].x])%100003;//计算点
            }
            t=a[t].next;//下一条边
        }
        v[state[head]]=false;//解封
    }
    for (int i=1;i<=n;i++)
      printf("%d\n",s[i]);//输出
}



















*其实我看了题解*

你可能感兴趣的:(图论)