bzoj1875 HH去散步
Posted cn-suqingnian
tags:
篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了bzoj1875 HH去散步相关的知识,希望对你有一定的参考价值。
一开始特别天真,
$Folyd$传递闭包写了一下过了样例就交上去了
然后$gg$
$qwq$
想了想$……$
还要写一点东西
最后统计答案的时候有细节要注意
/************************************************************** Problem: 1875 User: zhangheran Language: C++ Result: Accepted Time:17164 ms Memory:3876 kb ****************************************************************/ // luogu-judger-enable-o2 #include<iostream> #include<cstdio> //#include"suqingnian.h" #include<algorithm> #include<cstring> using namespace std; const int mod=45989; int n,m,t,a,b; struct data{ int v;int u;int next; }edge[410];int alist[410];int cnt; void add(int u,int v) { edge[++cnt].u=u; edge[cnt].v=v; edge[cnt].next=alist[u]; alist[u]=cnt; return ; } struct Martix{ long long num[220][220]; void hint(){memset(num,0,sizeof(num));for(int i=0;i<=m*2;i++) num[i][i]=1;} void clear(){memset(num,0,sizeof(num));} friend Martix operator *(const Martix &a,const Martix &b) { Martix c; memset(c.num,0,sizeof(c.num)); for(int k=0;k<=m*2;k++) for(int i=0;i<=m*2;i++) for(int j=0;j<=m*2;j++) c.num[i][j]=(c.num[i][j]+a.num[i][k]*b.num[k][j]%mod)%mod; return c; } friend Martix operator +(const Martix &a,const Martix &b) { Martix c;memset(c.num,0,sizeof(c.num)); for(int i=0;i<=m*2;i++) for(int j=0;j<=m*2;j++) c.num[i][j]=(a.num[i][j]+b.num[i][j])%mod; return c; } }; Martix _pow(Martix _a,int _b) { Martix _res;_res.hint(); for(;_b;_b >>= 1, _a= _a * _a ) if(_b & 1) _res = _res * _a ; return _res ; } int u,v; Martix map,dis; int ans=0; int main() { memset(alist,-1,sizeof(alist)); scanf("%d%d%d%d%d",&n,&m,&t,&a,&b); a++,b++; for(int i=1;i<=m;i++) scanf("%d%d",&u,&v),add(u+1,v+1),add(v+1,u+1); int next=alist[a]; while(next!=-1) map.num[0][next]++,next=edge[next].next; for(int i=1;i<=cnt;i++){ v=edge[i].v,next=alist[v]; while(next!=-1){ if(next!=(i+((i&1)?1:-1))) dis.num[i][next]++; next=edge[next].next; } } dis=_pow(dis,t-1); map=map*dis; // for(int i=0;i<=m*2;i++,puts("")) // for(int j=0;j<=m*2;j++) // printf("%d ",map.num[i][j]); for(int i=1;i<=cnt;i++) if(edge[i].v==b) ans=(ans+map.num[0][i])%mod; printf("%d",ans); return 0; }
以上是关于bzoj1875 HH去散步的主要内容,如果未能解决你的问题,请参考以下文章
bzoj 1875: [SDOI2009]HH去散步 -- 矩阵乘法
BZOj-1875: [SDOI2009]HH去散步 (矩阵快速幂)