ACM模板 - 持续更新中
KMP
1 char s[10020],t[1000020]; 2 int lens,lent; 3 int nextt[10020]; 4 void getnext() 5 { 6 int i=0,j=-1; 7 nextt[0]=-1; 8 while(i<lens) 9 { 10 if(j<0||s[i]==s[j]) 11 { 12 nextt[++i]=++j; 13 } 14 else 15 j=nextt[j]; 16 } 17 } 18 19 int kmp() 20 { 21 int i=0,j=0,ans=0; 22 while(i<lent) 23 { 24 if(j<0||t[i]==s[j]) 25 { 26 i++; 27 j++; 28 } 29 else 30 j=nextt[j]; 31 if(j==lens) 32 { 33 ans++; 34 j=nextt[j]; 35 } 36 } 37 return ans;
最短路
1 #include <stdio.h> 2 #include <string.h> 3 #include <algorithm> 4 using namespace std; 5 #define inf 0x3f3f3f3f 6 int dp[1010][1010]; 7 int dis[10050],vis[10050]; 8 int n,m; 9 void djk(int s) 10 { 11 for(int i=0;i<n;i++){ 12 vis[i]=0; 13 dis[i]=inf; 14 } 15 vis[s]=1; 16 dis[s]=0; 17 for(int i=0;i<n;i++) 18 { 19 int u,minn=inf; 20 for(int j=0;j<n;j++) 21 { 22 if(!vis[j]&&minn>dis[j]) 23 { 24 minn=dis[j]; 25 u=j; 26 } 27 } 28 vis[u]=1; 29 for(int j=0;j<n;j++) 30 { 31 if(!vis[j]&&dis[j]>dis[u]+dp[u][j]) 32 { 33 dis[j]=dis[u]+dp[u][j]; 34 } 35 } 36 } 37 } 38 int main(){ 39 while(~scanf("%d%d",&n,&m)&&(n+m)){ 40 memset(dp,inf,sizeof(dp)); 41 for(int i=1;i<=m;i++){ 42 int u,v,w; 43 scanf("%d%d%d",&u,&v,&w); 44 if(dp[u][v]>w) 45 dp[u][v]=dp[v][u]=w; 46 } 47 int x,y; 48 scanf("%d%d",&x,&y); 49 djk(x); 50 if(dis[y]==inf) 51 printf("-1\n"); 52 else printf("%d\n",dis[y]); 53 } 54 }
网络流EK/Dinic
1 #include <stdio.h> 2 #include <string.h> 3 #include <algorithm> 4 #include <queue> 5 using namespace std; 6 #define inf 0x3f3f3f3f 7 #define N 250 8 int head[N],vis[N],tot,deep[N]; 9 int m,n; 10 struct node{ 11 int to,nex,cap; 12 }e[N<<1]; 13 14 void init() 15 { 16 memset(deep,0,sizeof(deep)); 17 memset(head,-1,sizeof(head)); 18 tot=0; 19 } 20 21 void add(int u,int v,int w) 22 { 23 e[tot].to=v; 24 e[tot].cap=w; 25 e[tot].nex=head[u]; 26 head[u]=tot++; 27 } 28 29 bool bfs(int s,int t) 30 { 31 memset(vis,0,sizeof(vis)); 32 queue<int>q; 33 vis[s]=1; 34 deep[s]=0; 35 deep[t]=-1; 36 while(!q.empty()) q.pop(); 37 q.push(s); 38 while(!q.empty()) 39 { 40 int now=q.front(); q.pop(); 41 for(int i=head[now];i!=-1;i=e[i].nex) 42 { 43 int to=e[i].to; 44 if(vis[to]||e[i].cap<=0) continue; 45 vis[to]=1; 46 deep[to]=deep[now]+1; 47 q.push(to); 48 } 49 } 50 if(deep[t]==-1) return false; 51 return true; 52 } 53 54 int dfs(int u,int t,int flow) 55 { 56 int res=0,f=0; 57 if(u==t||flow==0) return flow; 58 for(int i=head[u];i!=-1;i=e[i].nex){ 59 int to=e[i].to; 60 if(deep[to]==deep[u]+1) 61 { 62 f=dfs(to,t,min(flow,e[i].cap)); 63 if(f<=0) continue; 64 e[i].cap-=f; 65 e[i^1].cap+=f; 66 flow-=f; 67 res+=f; 68 if(flow<=0) break; 69 } 70 } 71 return res; 72 } 73 74 int Dinic(int s,int t){ 75 int ans=0; 76 while(bfs(s,t)) 77 { 78 ans+=dfs(s,t,inf); 79 } 80 return ans; 81 } 82 83 int main(){ 84 while(~scanf("%d%d",&m,&n)&&(n+m)) 85 { 86 init(); 87 for(int i=1;i<=m;i++) 88 { 89 int u,v,w; 90 scanf("%d%d%d",&u,&v,&w); 91 add(u,v,w); 92 add(v,u,0); 93 } 94 printf("%d\n",Dinic(1,n)); 95 } 96 }
最长公共子序列:
D - D
1 #include<stdio.h> 2 #include<string.h> 3 #include<queue> 4 #include<set> 5 #include<iostream> 6 #include<map> 7 #include<stack> 8 #include<cmath> 9 #include<algorithm> 10 #define ll long long 11 using namespace std; 12 char s1[1001],s2[1001]; 13 int dp[1001][1001]; 14 int main() 15 { 16 while(~scanf("%s %s",s1+1,s2+1)) 17 { 18 19 int l1=strlen(s1+1); 20 int l2=strlen(s2+1); 21 for(int i=1;i<=l1;i++) 22 { 23 for(int j=1;j<=l2;j++) 24 { 25 if(s1[i]==s2[j]) 26 dp[i][j]=dp[i-1][j-1]+1; 27 else 28 dp[i][j]=max(dp[i-1][j],dp[i][j-1]); 29 } 30 } 31 printf("%d\n",dp[l1][l2]); 32 } 33 }
线段树
F - Just a Hook
1 #include <stdio.h> 2 #include <string.h> 3 int lazy[400040],tree[400040]; 4 5 void build(int L,int R,int idx) 6 { 7 if(L==R) 8 { 9 tree[idx]=1; 10 return ; 11 } 12 int mid=(L+R)/2; 13 build(L,mid,idx*2); 14 build(mid+1,R,idx*2+1); 15 tree[idx]=tree[idx*2]+tree[idx*2+1]; 16 } 17 void pushdown(int len,int idx) 18 { 19 if(lazy[idx]) 20 { 21 lazy[idx*2]=lazy[idx]; 22 lazy[idx*2+1]=lazy[idx]; 23 tree[idx*2]=lazy[idx]*(len-len/2); 24 tree[idx*2+1]=lazy[idx]*(len/2); 25 lazy[idx]=0; 26 } 27 } 28 void update(int L,int R,int x,int y,int z,int idx) 29 { 30 if(x<=L&&R<=y) 31 { 32 tree[idx]=(R-L+1)*z; 33 lazy[idx]=z; 34 return ; 35 } 36 pushdown(R-L+1,idx); 37 int mid=(L+R)/2; 38 if(x<=mid) 39 update(L,mid,x,y,z,idx*2); 40 if(y>=mid+1) 41 update(mid+1,R,x,y,z,idx*2+1); 42 tree[idx]=tree[idx*2]+tree[idx*2+1]; 43 } 44 45 int main() 46 { 47 int t,n,w,x,y,z; 48 scanf("%d",&t); 49 for(int i=1;i<=t;i++) 50 { 51 memset(lazy,0,sizeof(lazy)); 52 scanf("%d%d",&n,&w); 53 build(1,n,1); 54 while(w--) 55 { 56 scanf("%d%d%d",&x,&y,&z); 57 update(1,n,x,y,z,1); 58 } 59 printf("Case %d: The total value of the hook is %d.\n",i,tree[1]); 60 } 61 62 }
马拉车:
最长回文
1 #include <stdio.h> 2 #include <stdlib.h> 3 #include <string.h> 4 #include <algorithm> 5 #define Max 110005 6 using namespace std; 7 char ma[Max*2]; 8 int mp[Max*2]; 9 void manacher(char s[],int len) 10 { 11 int l=0; 12 ma[l++]='$'; 13 ma[l++]='#'; 14 for(int i=0;i<len;i++) 15 { 16 ma[l++]=s[i]; 17 ma[l++]='#'; 18 } 19 /* a b a b c */ 20 /*$ # a # b # a # b # c # */ 21 ma[l]=0; 22 int mx=0,id=0;//mx为以id为中心的最长回文串的右界 id+p[id]=mx [id-p[id]~mx] 23 //若遍历到i,有i<mx :if(i<mx) p[i]=min(p[j=2*id-i],mx-i) 24 for(int i=0;i<l;i++) 25 { 26 mp[i]=mx>i?min(mp[2*id-i],mx-i):1; 27 while(ma[i+mp[i]]==ma[i-mp[i]]) // 不需边界判断,因为左有'$',右有'\0' 28 mp[i]++;//j 回文串左端正好与 id 的回文串左端重合时 29 // 我们每走一步 i,都要和 mx 比较,我们希望 mx 尽可能的远,这样才能更有机会执行 if (i < mx)这句代码,从而提高效率 30 if(i+mp[i]>mx)//更新 id,mx; 31 { 32 mx=i+mp[i]; 33 id=i; 34 } 35 } 36 } 37 char s[Max]; 38 int main() 39 { 40 while(~scanf("%s",s)) 41 { 42 int len=strlen(s),ans=0; 43 manacher(s,len); 44 for(int i=0;i<2*len+2;i++) 45 ans=max(ans,mp[i]-1);//性质:最长回文长度=mp[i]-1; mp[i]个'#',mp[i]-1个字符,原长2*mp[i]-1; 46 printf("%d\n",ans); 47 } 48 }
最大流最小花费
Going Home
1 #include <cstdio> 2 #include <cstring> 3 #include <algorithm> 4 #include <queue> 5 #include <cmath> 6 using namespace std; 7 const int MAXN = 10000; 8 const int MAXM = 100000; 9 const int inf = 0x3f3f3f3f; 10 struct Edge 11 { 12 int to, next, cap, flow, cost; 13 int x, y; 14 }e[MAXM],HH[MAXN],MM[MAXN]; 15 int head[MAXN],tol; 16 int pre[MAXN],cost[MAXN]; 17 bool vis[MAXN]; 18 int N, M; 19 char map[MAXN][MAXN]; 20 void init(){ 21 N=MAXN; 22 tol=0; 23 memset(head,-1,sizeof(head)); 24 } 25 void add(int u,int v,int cap,int cost){ 26 e[tol].to=v; 27 e[tol].cap=cap; 28 e[tol].cost=cost; 29 e[tol].flow=0; 30 e[tol].next=head[u]; 31 head[u]=tol++; 32 33 e[tol].to=u; 34 e[tol].cap=0; 35 e[tol].cost=-cost; 36 e[tol].flow=0; 37 e[tol].next=head[v]; 38 head[v]=tol++; 39 } 40 41 bool spfa(int s,int t){ 42 queue<int >q; 43 for(int i=0;i<N;i++){ 44 pre[i]=-1; 45 vis[i]=false; 46 cost[i]=inf; 47 } 48 cost[s]=0; 49 vis[s]=true; 50 q.push(s); 51 while(!q.empty()){ 52 int u=q.front();q.pop(); 53 vis[u]=false; 54 for(int i=head[u];i!=-1;i=e[i].next){ 55 int to=e[i].to; 56 if(e[i].cap>e[i].flow&&cost[to]>cost[u]+e[i].cost){ 57 cost[to]=cost[u]+e[i].cost; 58 pre[to]=i; 59 if(!vis[to]){ 60 vis[to]=true; 61 q.push(to); 62 } 63 } 64 } 65 } 66 if(pre[t] == -1) return false; 67 else return true; 68 } 69 70 int mincostmaxflow(int s,int t,int &cost){ 71 int flow=0; 72 cost=0; 73 while(spfa(s,t)){ 74 int f=inf; 75 for(int i=pre[t];i!=-1;i=pre[e[i^1].to]){ 76 f=min(f,e[i].cap-e[i].flow); 77 } 78 for(int i=pre[t];i!=-1;i=pre[e[i^1].to]){ 79 e[i].flow+=f; 80 e[i^1].flow-=f; 81 cost+=e[i].cost*f; 82 } 83 flow+=f; 84 } 85 return flow; 86 } 87 int main(){ 88 int n, m; 89 while(~scanf("%d%d",&n,&m)) 90 { 91 if(n==0 && m==0) 92 break; 93 int ch = 0, cm = 0; 94 init();//注意 95 for(int i = 0; i < n; i++) 96 { 97 scanf("%s",map[i]); 98 for(int j = 0; j < m; j++) 99 { 100 if(map[i][j]=='H') 101 { 102 HH[ch].x = i; 103 HH[ch++].y = j; 104 } 105 else if(map[i][j]=='m') 106 { 107 MM[cm].x = i; 108 MM[cm++].y = j; 109 } 110 } 111 } 112 int beg = 0;//超级起点 113 int end = 2*ch+1;//超级汇点 114 for(int i=0;i<cm;i++){ 115 add(beg,i+1,1,0); 116 for(int j=0;j<ch;j++){ 117 int tt = abs(HH[i].x-MM[j].x)+abs(HH[i].y-MM[j].y);//花费 118 add(i+1,j+1+ch,1,tt); 119 } 120 add(i+1+ch,end,1,0); 121 } 122 int ans=0; 123 mincostmaxflow(beg,end,ans); 124 printf("%d\n",ans); 125 } 126 }
浙公网安备 33010602011771号