-
T1 数学老师的报复
矩阵快速幂模板,类似于菲波那切数列的矩阵
[1,1]*[A,1
B,0]
1 #include <cstdio> 2 3 #define LL long long 4 inline void read(LL &x) 5 { 6 x=0; register char ch=getchar(); register bool _=0; 7 for(; ch>'9'||ch<'0'; ch=getchar()) if(ch=='-') _=1; 8 for(; ch>='0'&&ch<='9'; ch=getchar()) x=x*10+ch-'0'; 9 x=_?((~x)+1):x; 10 } 11 const int mod(7); 12 LL a,b,n; 13 14 struct Matrix_fb { 15 LL e[2][2]; 16 Matrix_fb operator * (Matrix_fb x) const 17 { 18 Matrix_fb ret; 19 for(int i=0; i<2; ++i) 20 for(int j=0; j<2; ++j) 21 { 22 ret.e[i][j]=0; 23 for(int k=0; k<2; ++k) 24 ret.e[i][j]+=e[i][k]*x.e[k][j],ret.e[i][j]%=mod; 25 } 26 return ret; 27 } 28 } ans,base; 29 30 int Presist() 31 { 32 // freopen("attack.in","r",stdin); 33 // freopen("attack.out","w",stdout); 34 35 read(a),read(b),read(n); 36 if(n<=2) { puts("1"); return 0; } 37 ans.e[0][0]=ans.e[0][1]=1; 38 ans.e[1][0]=ans.e[1][1]=0; 39 base.e[0][0]=a%7,base.e[0][1]=1, 40 base.e[1][0]=b%7,base.e[1][1]=0; 41 for(n-=2; n; n>>=1,base=base*base) 42 if(n&1) ans=ans*base; 43 printf("%lld ",ans.e[0][0]); 44 return 0; 45 } 46 47 int Aptal=Presist(); 48 int main(int argc,char**argv){;}
-
T2 和生物老师的战争
1 #include <cstdio> 2 3 inline void read(int &x) 4 { 5 x=0; register char ch=getchar(); 6 for(; ch>'9'||ch<'0'; ) ch=getchar(); 7 for(; ch>='0'&&ch<='9'; ch=getchar()) x=x*10+ch-'0'; 8 } 9 10 int Presist() 11 { 12 freopen("fseq.in","r",stdin); 13 freopen("fseq.out","w",stdout); 14 int t; read(t); 15 for(int n,m; t--; ) 16 { 17 read(n),read(m); 18 if(n<m) puts("0.000000"); 19 else 20 { 21 double fz=n-m+1; 22 double fm=n+1; 23 printf("%.6lf ",fz/fm); 24 } 25 } 26 return 0; 27 } 28 29 int Aptal=Presist(); 30 int main(int argc,char**argv){;}
-
T3 化学竞赛的大奖
1 #include <cstring> 2 #include <cstdio> 3 #include <queue> 4 5 #define LL long long 6 #define min(a,b) (a<b?a:b) 7 #define max(a,b) (a>b?a:b) 8 9 inline void read(int &x) 10 { 11 x=0; register char ch=getchar(); 12 for(; ch>'9'||ch<'0'; ) ch=getchar(); 13 for(; ch>='0'&&ch<='9'; ch=getchar()) x=x*10+ch-'0'; 14 } 15 const int N(20000+15); 16 const int M(200000+5); 17 int n,m; 18 int head[2][N],sumedge[2]; 19 struct Edge { 20 int v,next,w; 21 Edge(int v=0,int next=0,int w=0):v(v),next(next),w(w){} 22 }edge[2][M<<1]; 23 inline void ins(int u,int v,int w,int op) 24 { 25 edge[op][++sumedge[op]]=Edge(v,head[op][u],w),head[op][u]=sumedge[op]; 26 edge[op][++sumedge[op]]=Edge(u,head[op][v],w),head[op][v]=sumedge[op]; 27 } 28 29 int tim,dfn[N],low[N]; 30 int top,sta[N],insta[N]; 31 int sumcol,col[N]; 32 void DFS(int u,int pre) 33 { 34 low[u]=dfn[u]=++tim; 35 sta[++top]=u, insta[u]=1; 36 for(int v,i=head[0][u]; i; i=edge[0][i].next) 37 { 38 /*if(vis[i]||vis[i^1]) continue; 39 vis[i]=vis[i^1]=true;*/ 40 v=edge[0][i].v; if(v==pre) continue; 41 if(!dfn[v]) DFS(v,u),low[u]=min(low[u],low[v]); 42 else if(insta[v]) low[u]=min(low[u],dfn[v]); 43 } 44 if(low[u]==dfn[u]) 45 { 46 col[u]=++sumcol; 47 for(; u!=sta[top]; top--) 48 { 49 col[sta[top]]=sumcol; 50 insta[sta[top]]=false; 51 } 52 insta[u]=false, top--; 53 } 54 } 55 56 struct Node { 57 int pos; LL dis; 58 bool operator < (const Node&x)const 59 { 60 return dis<x.dis; 61 } 62 }u,v; 63 std::priority_queue<Node>que; 64 LL dis[N],ans[N]; 65 bool vis[N]; 66 inline void Dijkstra(int s) 67 { 68 for(; !que.empty(); ) que.pop(); 69 for(int i=1; i<=sumcol; ++i) 70 dis[i]=-1,vis[i]=false; 71 72 dis[s]=u.dis=0,u.pos=s; que.push(u); 73 for(; !que.empty(); ) 74 { 75 u=que.top(); que.pop(); 76 if(vis[u.pos]) continue; vis[u.pos]=1; 77 for(int i=head[1][u.pos]; i; i=edge[1][i].next) 78 { 79 v.pos=edge[1][i].v; if(!vis[v.pos]) 80 if(dis[v.pos]<dis[u.pos]+edge[1][i].w) 81 { 82 v.dis=u.dis+(LL)edge[1][i].w; 83 ans[s]=max(ans[s],v.dis); 84 dis[v.pos]=v.dis; 85 que.push(v); 86 } 87 } 88 } 89 } 90 91 int Presist() 92 { 93 // freopen("prize.in","r",stdin); 94 // freopen("prize.out","w",stdout); 95 96 read(n),read(m); 97 for(int u,v,w,i=1; i<=m; ++i) 98 read(u),read(v),read(w),ins(u,v,w,0); 99 for(int i=1; i<=n; ++i) 100 if(!dfn[i]) DFS(i,-1); 101 102 for(int v,u=1; u<=n; ++u) 103 for(int i=head[0][u]; i; i=edge[0][i].next) 104 { 105 v=edge[0][i].v; if(col[u]==col[v]) continue; 106 ins(col[u],col[v],edge[0][i].w,1); 107 } 108 109 for(int i=1; i<=sumcol; ++i) ans[i]=-1, Dijkstra(i); 110 for(int i=1; i<=n; ++i) printf("%lld ",ans[col[i]]); 111 return 0; 112 } 113 114 int Aptal=Presist(); 115 int main(int argc,char**argv){;}
可以先求出强连通分量,两次dfs得到数的直径,ans[i]=max(dis(s,i),dis(t,i))
1 #include <cstring> 2 #include <cstdio> 3 4 #define min(a,b) (a<b?a:b) 5 #define max(a,b) (a>b?a:b) 6 7 inline void read(int &x) 8 { 9 x=0; register char ch=getchar(); 10 for(; ch>'9'||ch<'0'; ) ch=getchar(); 11 for(; ch>='0'&&ch<='9'; ch=getchar()) x=x*10+ch-'0'; 12 } 13 14 const int N(20000+15); 15 const int M(200000+5); 16 17 int n,m; 18 int head[2][N],sumedge[2]; 19 struct Edge { 20 int v,next,w; 21 Edge(int v=0,int next=0,int w=0):v(v),next(next),w(w){} 22 }edge[2][M<<1]; 23 inline void ins(int u,int v,int w,int op) 24 { 25 edge[op][++sumedge[op]]=Edge(v,head[op][u],w),head[op][u]=sumedge[op]; 26 if(!op) edge[op][++sumedge[op]]=Edge(u,head[op][v],w),head[op][v]=sumedge[op]; 27 } 28 29 int tim,dfn[N],low[N]; 30 int top,sta[N],insta[N]; 31 int sumcol,col[N]; 32 33 namespace Tarjan { 34 35 void DFS(int u,int pre) 36 { 37 low[u]=dfn[u]=++tim; 38 sta[++top]=u, insta[u]=1; 39 for(int v,i=head[0][u]; i; i=edge[0][i].next) 40 { 41 v=edge[0][i].v; 42 if(!dfn[v]) DFS(v,u),low[u]=min(low[u],low[v]); 43 else if(insta[v]&&v!=pre) low[u]=min(low[u],dfn[v]); 44 } 45 if(low[u]==dfn[u]) 46 { 47 col[u]=++sumcol; 48 for(; u!=sta[top]; top--) 49 { 50 col[sta[top]]=sumcol; 51 insta[sta[top]]=false; 52 } 53 insta[u]=false, top--; 54 } 55 } 56 inline void work() 57 { 58 for(int i=1; i<=n; ++i) 59 if(!dfn[i]) DFS(i,-1); 60 } 61 } 62 63 int dis[2][N],s,t,maxx; 64 namespace Solve { 65 void DFS(int u,int pre) 66 { 67 for(int v,i=head[1][u]; i; i=edge[1][i].next) 68 { 69 v=edge[1][i].v; if(pre==v) continue; 70 dis[0][v]=dis[0][u]+edge[1][i].w; 71 if(dis[0][v]>maxx) maxx=dis[0][v],s=v; 72 DFS(v,u); 73 } 74 } 75 void DFS_(int u,int pre) 76 { 77 for(int v,i=head[1][u]; i; i=edge[1][i].next) 78 { 79 v=edge[1][i].v; if(v==pre) continue; 80 dis[1][v]=dis[1][u]+edge[1][i].w; DFS_(v,u); 81 } 82 } 83 inline void work() 84 { 85 for(int v,u=1; u<=n; ++u) 86 for(int i=head[0][u]; i; i=edge[0][i].next) 87 { 88 v=edge[0][i].v; if(col[u]==col[v]) continue; 89 ins(col[u],col[v],edge[0][i].w,1); 90 } 91 DFS (1,-1); 92 for(int i=1; i<=sumcol; ++i) dis[0][i]=0; maxx=0; DFS (s,-1); 93 DFS_(s,-1); 94 for(int i=1; i<=n; ++i) 95 printf("%d ",max(dis[1][col[i]],dis[0][col[i]])); 96 } 97 98 } 99 100 int Presist() 101 { 102 freopen("prize.in","r",stdin); 103 freopen("prize.out","w",stdout); 104 105 read(n),read(m); 106 for(int u,v,w,i=1; i<=m; ++i) 107 read(u),read(v),read(w),ins(u,v,w,0); 108 Tarjan::work(); 109 Solve ::work(); 110 return 0; 111 } 112 113 int Aptal=Presist(); 114 int main(int argc,char**argv){;}