首页 > 代码库 > hdu 2157 How many ways?? (可达矩阵)

hdu 2157 How many ways?? (可达矩阵)

题意:给你一个有向图,从A 点到 B点恰好经过k个点的方案数 (k < 20), 可以走重复边

思路:利用离散数学中的可达矩阵,可达矩阵的K次幂便是从i到j走K步能到达的方案数

代码:

#include <cstdio>
#include <cstring>
#include <iostream>

using namespace std;

typedef long long ll;
int N,M,P;
const int MOD=1000;
//int MOD;
struct  Matrix
{
    ll m[25][25];
};

Matrix A;
Matrix I;

Matrix multi(Matrix a,Matrix b)
{
    Matrix ans;
    for(int i=0;i<N;i++)
    {
       for(int j=0;j<M;j++)
       {
          ans.m[i][j]=0;
          for(int k=0;k<P;k++)
          {
             ans.m[i][j]+=a.m[i][k]*b.m[k][j]%MOD;
          }
          ans.m[i][j]%=MOD;
       }
    }
    return ans;
}

Matrix power(Matrix a,int k)
{
    Matrix ans=I,p=a;
    while(k)
    {
      if(k&1)
      {
        ans=multi(ans,p);
      }
      k>>=1;
      p=multi(p,p);
    }
    return ans;
}

int main(int argc, char const *argv[])
{
    int m;
    while(cin>>N>>m)
    {
       if(N==0&&m==0) break;
       M=P=N;
       memset(A.m,0,sizeof(A.m));
       while(m--)
       {
          int a,b;
          scanf("%d %d",&a,&b);
          A.m[a][b]=1;
       }
       for(int i=0;i<N;i++)
       I.m[i][i]=1;
       int T;
       cin>>T;
       while(T--)
       {
           int st,ed,k;
           scanf("%d %d %d",&st,&ed,&k);
           Matrix ans = power(A,k);
           printf("%lld\n",ans.m[st][ed]);
       }
    }
       return 0;
}

 

hdu 2157 How many ways?? (可达矩阵)