zoukankan      html  css  js  c++  java
  • NOIP模板总结

    NOIP模板总结

      进考场先打一份缺省源:

      
     1 # include <cstdio>
     2 # include <iostream>
     3 # include <cstring>
     4 # include <string>
     5 # include <algorithm>
     6 # include <cmath>
     7 # define R register int
     8 # define ll long long
     9 
    10 using namespace std;
    11 
    12 int main()
    13 {
    14 
    15     return 0;
    16 }
    缺省源
      
     1 #include<bits/stdc++.h>
     2 using namespace std;
     3 int main()
     4 {
     5     int n=0;
     6     while(1)
     7     {
     8         printf("Test %d:
    ",++n);
     9         system("data.exe");
    10         system("my.exe");
    11         system("std.exe");
    12         if(system("fc std.out my.out"))
    13             puts("WA"),system("pause");
    14         else puts("AC");
    15     }
    16 }
    对拍
      
    1 # define r(a,b) (rand()*rand()%((b)-(a)+1)+(a))
    生成随机数
      
    1 int read()
    2 {
    3     int x=0,f=1;
    4     char c=getchar();
    5     while(!isdigit(c)) { if(c=='-') f=-f; c=getchar(); }
    6     while(isdigit(c)) x=(x<<3)+(x<<1)+(c^48),c=getchar();
    7     return x*f;
    8 }
    快读

      重启一下电脑看看是哪些盘不清空。

    调配置:

      ·工具->编译选项->代码警告->显示最多警告消息;

      ·工具->编译选项->连接器->产生调试信息;

      ·(如果$IDE$右边有奇怪的白色竖线):工具->编辑器属性->基本->右边缘->把勾去掉;

      ·工具->编辑器属性->高亮显示当前行->$Green$;

      ·工具->编辑器属性->显示->字体:$Andalus$->大小$10$;

      ·工具->编辑器属性->语法->预设$Obsidian$;

      虽然比不上$Vscode$漂亮,但是至少挺清楚的.

      本来想把数据结构都封装成结构体,后来发现没什么用处还容易错...等联赛完了再弄这些东西吧。

      前几篇模板都是全套的,大多数还在$OJ$上交过,后面的一些来不及写了只写了主要的函数,但是思路肯定是对的.

    图论:

      关于最小生成树,实测还是$kruscal$比较快,而且内存小,而且代码短.

      
    1 for (R k=1;k<=n;++k)
    2     for (R i=1;i<=n;++i)
    3         for (R j=1;j<=n;++j)
    4             g[i][j]=min(g[i][j],g[i][k]+g[k][j]);
    5             
    floyd
      
     1 # include <cstdio>
     2 # include <iostream>
     3 # include <queue>
     4 # include <cstring>
     5 # define ll long long
     6 # define R register int
     7 # define pac(a,b) make_pair(a,b)
     8 
     9 using namespace std;
    10 
    11 const int maxn=100005;
    12 const int maxm=200005;
    13 int n,m,s,h,firs[maxn],vis[maxn],x,y,z;
    14 ll d[maxn];
    15 struct edge
    16 {
    17     int too,nex,co;
    18 }g[maxm<<1];
    19 typedef pair <int,int> pii;
    20 priority_queue <pii,vector<pii>,greater<pii> >q;
    21 
    22 void add (int x,int y,int z)
    23 {
    24     g[++h].nex=firs[x];
    25     firs[x]=h;
    26     g[h].too=y;
    27     g[h].co=z;
    28 }
    29 
    30 int read()
    31 {
    32     int x=0;
    33     char c=getchar();
    34     while(!isdigit(c)) c=getchar();
    35     while(isdigit(c)) x=(x<<3)+(x<<1)+(c^48),c=getchar();
    36     return x;
    37 }
    38 
    39 void dij (int s)
    40 {
    41     int beg,j;
    42     memset(d,1,sizeof(d));
    43     d[s]=0;
    44     q.push(pac(0,s));
    45     while(q.size())
    46     {
    47         beg=q.top().second;
    48         q.pop();
    49         if(vis[beg]) continue;
    50         vis[beg]=true;
    51         for (R i=firs[beg];i;i=g[i].nex)
    52         {
    53             j=g[i].too;
    54             if(d[beg]+g[i].co>=d[j]) continue;
    55             d[j]=d[beg]+g[i].co;
    56             q.push(pac(d[j],j));
    57         }
    58     }
    59 }
    60 
    61 int main()
    62 {
    63     n=read(),m=read(),s=read();
    64     for (R i=1;i<=m;++i)
    65     {
    66         x=read(),y=read(),z=read();
    67         add(x,y,z);
    68     }
    69     dij(s);
    70     for (R i=1;i<=n;++i)
    71         printf("%lld ",d[i]);
    72     return 0;
    73 }
    Heap+dijkstra
      
     1 # include <cstdio>
     2 # include <iostream>
     3 # include <queue>
     4 # include <cstring>
     5 # define ll long long
     6 # define R register int
     7 # define pac(a,b) make_pair(a,b)
     8 
     9 using namespace std;
    10 
    11 const int maxn=100005;
    12 const int maxm=200005;
    13 int n,m,s,h,firs[maxn],vis[maxn],x,y,z;
    14 ll d[maxn],f[maxn];
    15 struct edge
    16 {
    17     int too,nex,co;
    18 }g[maxm<<1];
    19 typedef pair <int,int> pii;
    20 priority_queue <pii,vector<pii>,greater<pii> >q;
    21 
    22 void add (int x,int y,int z)
    23 {
    24     g[++h].nex=firs[x];
    25     firs[x]=h;
    26     g[h].too=y;
    27     g[h].co=z;
    28 }
    29 
    30 int read()
    31 {
    32     int x=0;
    33     char c=getchar();
    34     while(!isdigit(c)) c=getchar();
    35     while(isdigit(c)) x=(x<<3)+(x<<1)+(c^48),c=getchar();
    36     return x;
    37 }
    38 
    39 void dij (int s)
    40 {
    41     int beg,j;
    42     memset(d,1,sizeof(d));
    43     d[s]=0;
    44     f[s]=1;
    45     q.push(pac(0,s));
    46     while(q.size())
    47     {
    48         beg=q.top().second;
    49         q.pop();
    50         if(vis[beg]) continue;
    51         vis[beg]=true;
    52         for (R i=firs[beg];i;i=g[i].nex)
    53         {
    54             j=g[i].too;
    55             if(d[beg]+g[i].co>d[j]) continue;
    56             if(d[beg]+g[i].co==d[j]) f[j]+=f[beg];
    57             else
    58             {
    59                 f[j]=f[beg];
    60                 d[j]=d[beg]+g[i].co;
    61                 q.push(pac(d[j],j));
    62             }
    63         }
    64     }
    65 }
    66 
    67 int main()
    68 {
    69     n=read(),m=read(),s=read();
    70     for (R i=1;i<=m;++i)
    71     {
    72         x=read(),y=read(),z=read();
    73         add(x,y,z);
    74     }
    75     dij(s);
    76     for (R i=1;i<=n;++i)
    77         printf("%lld ",f[i]);
    78     return 0;
    79 }
    最短路计数
      
     1 # include <cstdio>
     2 # include <iostream>
     3 # include <queue>
     4 # include <cstring>
     5 # define ll long long
     6 # define R register int
     7 
     8 using namespace std;
     9 
    10 const int maxn=100005;
    11 const int maxm=200005;
    12 int n,m,s,h,firs[maxn],vis[maxn],x,y,z;
    13 ll d[maxn],f[maxn];
    14 struct edge
    15 {
    16     int too,nex,co;
    17 }g[maxm<<1];
    18 queue <int> q;
    19 
    20 void add (int x,int y,int z)
    21 {
    22     g[++h].nex=firs[x];
    23     firs[x]=h;
    24     g[h].too=y;
    25     g[h].co=z;
    26 }
    27 
    28 int read()
    29 {
    30     int x=0;
    31     char c=getchar();
    32     while(!isdigit(c)) c=getchar();
    33     while(isdigit(c)) x=(x<<3)+(x<<1)+(c^48),c=getchar();
    34     return x;
    35 }
    36 
    37 void spfa (int s)
    38 {
    39     int beg,j;
    40     memset(d,1,sizeof(d));
    41     d[s]=0;
    42     q.push(s);
    43     while(q.size())
    44     {
    45         beg=q.front();
    46         q.pop();
    47         vis[beg]=false;
    48         for (R i=firs[beg];i;i=g[i].nex)
    49         {
    50             j=g[i].too;
    51             if(d[beg]+g[i].co>d[j]) continue;
    52         d[j]=d[beg]+g[i].co;
    53         if(!vis[j]) q.push(j),vis[j]=true;
    54         }
    55     }
    56 }
    57 
    58 int main()
    59 {
    60     n=read(),m=read(),s=read();
    61     for (R i=1;i<=m;++i)
    62     {
    63         x=read(),y=read(),z=read();
    64         add(x,y,z);
    65     }
    66     spfa(s);
    67     for (R i=1;i<=n;++i)
    68         printf("%lld ",d[i]);
    69     return 0;
    70 }
    spfa
      
     1 # include <cstdio>
     2 # include <iostream>
     3 # include <cstring>
     4 # include <string>
     5 # include <queue>
     6 # define R register int
     7 # define ll long long
     8 # define pac(a,b) make_pair(a,b)
     9 
    10 using namespace std;
    11 
    12 const int maxn=5003;
    13 const int maxm=200005;
    14 int n,m,h,firs[maxn],d[maxn],vis[maxn],x,y,z,ed[maxn];
    15 struct edge
    16 {
    17     int too,nex,co;
    18 }g[maxm<<1];
    19 typedef pair <int,int> pii;
    20 priority_queue <pii,vector<pii>,greater<pii> > q;
    21 
    22 void add (int x,int y,int z)
    23 {
    24     g[++h].nex=firs[x];
    25     firs[x]=h;
    26     g[h].too=y;
    27     g[h].co=z;
    28 }
    29 
    30 int main()
    31 {
    32     scanf("%d%d",&n,&m);
    33     for (R i=1;i<=m;++i)
    34     {
    35         scanf("%d%d%d",&x,&y,&z);
    36         add(x,y,z);
    37         add(y,x,z);
    38     }
    39     memset(d,1,sizeof(d));
    40     vis[1]=0,d[1]=0;
    41     q.push(pac(0,1));
    42     int j,beg;
    43     while(q.size())
    44     {
    45         beg=q.top().second;
    46         q.pop();
    47         if(vis[beg]) continue;
    48         vis[beg]=true;
    49         for (R i=firs[beg];i;i=g[i].nex)
    50         {
    51             j=g[i].too;
    52             if(vis[j]) continue;
    53             d[j]=min(d[j],g[i].co);
    54             q.push(pac(d[j],j));
    55         }
    56     }
    57     for (R i=1;i<=n;++i)
    58         if(!vis[j]) 
    59         {
    60             printf("orz");
    61             return 0;
    62         }
    63     int ans=0;
    64     for (R i=1;i<=n;++i)
    65         ans+=d[i];
    66     printf("%d",ans);
    67     return 0;
    68 }
    Heap+Prim
      
     1 # include <cstdio>
     2 # include <iostream>
     3 # include <cstring>
     4 # include <string>
     5 # include <algorithm>
     6 # define R register int
     7 # define ll long long
     8 
     9 using namespace std;
    10 
    11 const int maxn=5003;
    12 const int maxm=200005;
    13 int n,m,h,f[maxn],z[maxn],S,fx,fy,ans;
    14 struct ed
    15 {
    16     int x,y,z;
    17 }g[maxm];
    18 
    19 bool cmp (ed a,ed b) { return a.z<b.z; }
    20 int father (int x) { if(x!=f[x]) return f[x]=father(f[x]); return x; }
    21 
    22 int main()
    23 {
    24     scanf("%d%d",&n,&m);
    25     for (R i=1;i<=m;++i)
    26         scanf("%d%d%d",&g[i].x,&g[i].y,&g[i].z);
    27     sort(g+1,g+1+m,cmp);
    28     for (R i=1;i<=n;++i)
    29         f[i]=i,z[i]=1;
    30     S=n;
    31     for (R i=1;i<=m;++i)
    32     {
    33         fx=father(g[i].x);
    34         fy=father(g[i].y);
    35         if(fx==fy) continue;
    36         ans+=g[i].z;
    37         if(z[fx]>z[fy]) z[fx]+=z[fy],f[fy]=fx;
    38         else z[fy]+=z[fx],f[fx]=fy;
    39         S--;
    40     }
    41     if(S!=1) printf("orz");
    42     else printf("%d",ans);
    43     return 0;
    44 }
    Kruskal
      
     1     差分约束其实还是最短路,考的主要是一些建图:
     2         如果给出的式子有的是小于有的是大于,要先移项后再做;
     3     举个栗子:a[i]-a[j]<=c -> a[i]<=a[j]+c
     4     可以认为做一遍最短路后a[j]向a[i]连一条边权为c的边无法更新dis[i],所以连边后跑最短路;
     5     如果图不保证联通可以加一个虚点向其他所有点连边,边权视情况而定.
     6     一些基本的性质题目可能不说,但是自己要记得写:a[i]全为正时,s[i]>s[i-1],etc...
     7     求最大值跑最短路,最小值跑最长路.
     8     如果有负权边就只能用spfa,无解一般表现为又负环或者正环,用spfa判断.
     9     虽然很假,但是考场上要是真的不会做了可以考虑"梦想spfa",即运行时间过长时直接认为是负环.
    10     板子就不写了,和最短路差不多的.
    差分约束
      
     1 bool spfa()
     2 {
     3     memset(d,0x3f,sizeof(d));
     4     int j,beg;
     5     while (q.size()) q.pop();
     6     q.push(1);
     7     d[1]=0;
     8     while (q.size())
     9     {
    10         beg=q.front();
    11         q.pop();
    12         vis[beg]=0;
    13         for (int i=firs[beg];i;i=g[i].nex)
    14         {
    15             j=g[i].too;
    16             if(d[j]>d[beg]+g[i].co)
    17             {
    18                 d[j]=d[beg]+g[i].co;
    19                 s[j]=s[beg]+1;
    20                 if(s[j]>=n) return 1;
    21                 if(!vis[j])
    22                 {
    23                     vis[j]=1;
    24                     q.push(j);
    25                 }
    26             }
    27         }
    28     }
    29     return 0;
    30 }
    31 判断负环的方法很多,有时dfs的确实快,但是那个的复杂度根本不对,所以建议还是写这个。普通的spfa也有两种写法,一种是记录到每个点的最短路经过了几个点,还有一种是记录每个点入队几次,也许两者一起用是最好的吧,这里给出第一种做法。
    spfa判负环
      
     1 void init()
     2 {
     3     for (R i=2;i<=n;++i) lg[i]=lg[i>>1]+1;
     4 }
     5 
     6 void dfs (int x)
     7 {
     8     int j;
     9     for (R i=firs[x];i;i=g[i].nex)
    10     {
    11         j=g[i].too;
    12         if(dep[j]) continue;
    13         dep[j]=dep[x];
    14         f[j][0]=x;
    15         for (R k=1;k<=lg[ dep[j] ];++k)
    16             f[j][k]=f[ f[j][k-1] ][k-1];
    17         dfs(j);
    18     }
    19 }
    20 
    21 int lca (int x,int y)
    22 {
    23     if(dep[x]>dep[y]) swap(x,y);
    24     for (R i=lg[ dep[y] ];i>=0;--i)
    25         if(dep[y]-(1<<i)>=dep[x]) y=f[y][i];
    26     if(x==y) return x;
    27     for (R i=lg[ dep[x] ];i>=0;--i)
    28     {
    29         if(f[x][i]=f[y][i]) continue;
    30         x=f[x][i];
    31         y=f[y][i];
    32     }
    33     return f[x][0];
    34 }
    倍增求LCA
      
     1 # include <cstdio>
     2 # include <iostream>
     3 # define R register int
     4 
     5 using namespace std;
     6 
     7 int n,m,h,firs[maxn],r[maxn],c[maxn],x,y;
     8 struct edge
     9 {
    10     略去.
    11 };
    12 
    13 void dfs (int x)
    14 {
    15     int j,t;
    16     for (R &i=firs[x];i;i=g[i].nex) //这个&是优化时间复杂度的精髓所在啊!
    17     {
    18         if(vis[i]) continue;
    19         j=g[i].too;
    20         vis[i]=true;
    21         t=i;
    22         dfs(j);
    23         sta[++top]=t; //因为之前加过取地址符,所以i可能变了 :(
    24     }
    25 }
    26 
    27 int main()
    28 {
    29     scanf("%d%d",&n,&m);
    30     for (R i=1;i<=m;++i)
    31     {
    32         scanf("%d%d",&x,&y);
    33         r[x]++,c[y]++;
    34         add(x,y);
    35     }
    36     for (R i=1;i<=n;++i)
    37         if(r[i]!=c[i])
    38         {
    39             printf("NO");
    40             return 0;
    41         }
    42     for (R i=1;i<=n;++i) //图中可能有一些孤立点,但是因为欧拉回路的关键是边所以没有关系
    43         if(firs[i])
    44         {
    45             dfs(i);
    46             break;
    47         }
    48     for (R i=Top;i>=1;--i) printf("%d ",sta[i]);
    49     return 0;
    50 }
    欧拉回路-有向图
      
     1 # include <cstdio>
     2 # include <iostream>
     3 # define R register int
     4 
     5 using namespace std;
     6 
     7 int n,m,h,firs[maxn],r[maxn],c[maxn],x,y;
     8 struct edge
     9 {
    10     略去.
    11 };
    12 
    13 void dfs (int x)
    14 {
    15     int j,ID;
    16     for (R &i=firs[x];i;i=g[i].nex) //这个&是优化时间复杂度的精髓所在啊!
    17     {
    18         ID=g[i].id;
    19         if(ID<0) ID=-ID;
    20         if(vis[ ID ]) continue;
    21         j=g[i].too;
    22         vis[ ID ]=true;
    23         dfs(j);
    24         sta[++top]=ID; //因为之前加过取地址符,所以i可能变了 :(
    25     }
    26 }
    27 
    28 int main()
    29 {
    30     scanf("%d%d",&n,&m);
    31     for (R i=1;i<=m;++i)
    32     {
    33         scanf("%d%d",&x,&y);
    34         d[x]++,d[y]++;
    35         add(x,y,i);
    36         add(y,x,-i);
    37     }
    38     for (R i=1;i<=n;++i)
    39         if(d[i]%2)
    40         {
    41             printf("NO");
    42             return 0;
    43         }
    44     for (R i=1;i<=n;++i) //图中可能有一些孤立点,但是因为欧拉回路的关键是边所以没有关系
    45         if(firs[i])
    46         {
    47             dfs(i);
    48             break;
    49         }
    50     for (R i=Top;i>=1;--i) printf("%d ",sta[i]);
    51     return 0;
    52 }
    欧拉回路-无向图
      
     1 # include <cstdio>
     2 # include <iostream>
     3 # include <cstring>
     4 # include <string>
     5 # include <cmath>
     6 # include <algorithm>
     7 # define R register int
     8 # define ll long long
     9 
    10 using namespace std;
    11 
    12 const int maxn=100005;
    13 const int maxm=200005;
    14 int n,m,x,y,h,firs[maxn],d[maxn],f[maxn],z[maxn],od[maxn];
    15 struct edge
    16 {
    17     int too,nex;
    18 }g[maxm<<1];
    19 
    20 int father (int x) { if(x!=f[x]) return f[x]=father(f[x]); return x; }
    21 
    22 inline void uni (int x,int y)
    23 {
    24     int fx=father(x);
    25     int fy=father(y);
    26     if(fx==fy) return ;
    27     if(z[fx]>z[fy]) f[fy]=fx,z[fx]+=z[fy];
    28     else f[fx]=fy,z[fy]+=z[fx];
    29 }
    30 
    31 int main()
    32 {
    33     while(scanf("%d%d",&n,&m)!=EOF)
    34     {
    35         h=1;
    36         memset(d,0,sizeof(d));
    37         memset(firs,0,sizeof(firs));
    38         memset(od,0,sizeof(od));
    39         for (R i=1;i<=n;++i) f[i]=i,z[i]=1;
    40         for (R i=1;i<=m;++i)
    41         {
    42             scanf("%d%d",&x,&y);
    43             d[x]++,d[y]++;
    44             uni(x,y);
    45         }
    46         for (R i=1;i<=n;++i) f[i]=father(i);        
    47         for (R i=1;i<=n;++i) if(d[i]&1) od[ f[i] ]++;
    48         int ans=0;
    49         for (R i=1;i<=n;++i)
    50             if(f[i]==i&&z[i]!=1) ans+=max(1,od[i]/2);
    51         printf("%d
    ",ans);
    52     }
    53     return 0;
    54 }
    有向图最少笔画数
      
    1 欧拉道路就是把每条边不重不漏的经过一次的道路啦。
    2 无向图:1.图连通;
    3        2.有0/2个奇点;
    4 
    5 有向图:1:图连通;
    6        2:所有点的入度出度均相等或一点的入度比出度大一,一点入度比出度小一。
    欧拉道路相关
      
     1 void dfs (int x,int f)
     2 {
     3     id[x]=low[x]=++cnt;
     4     int j,son_cnt=0;
     5     for (R i=firs[x];i;i=g[i].nex)
     6     {
     7         j=g[i].too;
     8         if(!id[j])
     9         {
    10             dfs(j,x);
    11             son_cnt++;
    12             low[x]=min(low[x],low[j]);
    13             if(low[j]>=id[x]) cutt[x]=true;
    14         }
    15         else low[x]=min(low[x],id[j]);
    16     }
    17     if(f==0&&son_cnt>=2) cutt[x]=true;
    18 }
    Tarjan-割点
      
     1 void dfs (int x,int las)
     2 {
     3     id[x]=low[x]=++cnt;
     4     int j,son_cnt=0;
     5     for (R i=firs[x];i;i=g[i].nex)
     6     {
     7         if(i==(las^1)) continue;
     8         j=g[i].too;
     9         if(!id[j])
    10         {
    11             dfs(j,i);
    12             low[x]=min(low[x],low[j]);
    13             if(low[j]>id[x]) g[i].t=t[i^1].t=1;
    14         }
    15         else
    16             low[x]=min(low[x],id[j]);
    17     }
    18 }
    Tarjan-桥
      
     1 void dfs (int x)
     2 {
     3     id[x]=low[x]=++cnt;
     4     vis[x]=true;
     5     sta[++Top]=x;
     6     int j;
     7     for (R i=firs[x];i;i=g[i].nex)
     8     {
     9         j=g[i].too;
    10         if(!id[j])
    11         {
    12             dfs(j);
    13             low[x]=min(low[x],low[j]);
    14         }
    15         else if(vis[j]) low[x]=min(low[x],id[j]);
    16     }
    17     if(low[x]==id[x])
    18     {
    19         col[x]=++bp;
    20         vis[x]=0;
    21         while(sta[Top]!=x)
    22         {
    23             col[ sta[Top] ]=bp;
    24             vis[ sta[Top] ]=0;
    25             Top--;
    26         }
    27         Top--;
    28     }
    29 }
    Tarjan-强连通
      
    1 找出桥后删掉所有的桥,每个联通块就是一个边双。
    Tarjan-边双
      
     1 void dfs(int x,int f)
     2 {
     3     id[x]=low[x]=++cnt;
     4     int j,sz=0,k;
     5     for (R i=firs[x];i;i=g[i].nex)
     6     {
     7         j=g[i].too;
     8         if(!id[j])
     9         {
    10             sz++,sta[++Top]=i;
    11             dfs(j,x);
    12             low[x]=min(low[j],low[x]);
    13             if(low[j]>=id[x])
    14             {
    15                 v[x]=true;
    16                 bp++;
    17                 do
    18                 {
    19                     k=sta[Top];
    20                     if(col[ g[k].fro ]!=bp)
    21                     {
    22                         col[ g[k].fro ]=bp;
    23                         v_dcc[bp].push_back(g[k].fro);
    24                         siz[bp]++;
    25                     }
    26                     if(col[ g[k].too ]!=bp)
    27                     {
    28                         col[ g[k].too ]=bp;
    29                         v_dcc[bp].push_back(g[k].too);
    30                         siz[bp]++;
    31                     }
    32                     Top--;
    33                 }while(k!=i);
    34             }
    35         }else low[x]=min(low[x],id[j]);
    36     }
    37     if(f==0&&sz<=1) v[x]=false;
    38 }
    Tarjan-点双

    dp优化:

      注意矩阵乘法时一定要把$k$写在最外层循环,因为每次访问的内存连续所以可以快很多,真的快很多!

      
     1 struct mat
     2 {
     3     int n,m;
     4     ll a[maxn][maxn];
     5     void init()
     6     {
     7         memset(a,0,sizeof(a));
     8         for (R i=0;i<5;++i)
     9             a[i][i]=1;
    10     }
    11     void cler() { memset(a,0,sizeof(a)); }
    12     mat operator *  (const mat &a) const
    13     {
    14         mat c;
    15         c.cler();
    16         for (R k=0;k<a.m;++k)
    17             for (R i=0;i<this->n;++i)
    18                 for (R j=0;j<this->m;++j)    
    19                     c.a[i][j]=(c.a[i][j]+this->a[i][k]*a.a[k][j]%m)%m;
    20         c.n=n;
    21         c.m=a.m;
    22         return c;
    23     }
    24 };
    25 
    26 mat qui (mat a,int p)
    27 {
    28     mat ans;
    29     ans.init();
    30     ans.n=ans.m=5;
    31     while(p)
    32     {
    33         if(p&1) ans=ans*a;
    34         a=a*a;
    35         p>>=1;
    36     }
    37     return ans;
    38 }
    矩阵快速幂
      
     1 ll X (int i) { return ; }
     2 ll Y (int i) { return ; }
     3 ll K (int i) { return ; }
     4 ll B (int i) { return ; }
     5 double KK (int a,int b) {    if(X(b)==X(a)) return 0; return (double)(Y(b,j)-Y(a,j))/(X(b)-X(a));    }
     6 
     7 struct xq
     8 {
     9     int q[maxn];
    10     int h,t;
    11     void ins (int i)
    12     {
    13         int a,b,c;
    14         if(h<t) a=q[t-1],b=q[t],c=i;
    15         while(h<t&&KK(a,b)>KK(a,c))
    16         {
    17             t--;
    18             if(h<t) a=q[t-1],b=q[t],c=i;
    19         }
    20         q[++t]=i;
    21     }
    22     void del (int i)
    23     {
    24         int a,b;
    25         if(h<t) a=q[h],b=q[h+1];
    26         while(h<t&&KK(a,b)<K(i))
    27         {
    28             h++;
    29             if(h<t) a=q[h],b=q[h+1];    
    30         }    
    31     }
    32     void init() { h=1,t=0; }
    33     int firs () { return q[h]; }
    34 }q;
    基于单调队列的斜率优化

    数论算法:

      
     1 # include <cstdio>
     2 # include <iostream>
     3 # include <cstring>
     4 # include <string>
     5 # include <algorithm>
     6 # include <cmath>
     7 # define R register int
     8 # define ll long long
     9 
    10 using namespace std;
    11 
    12 ll a,b,p;
    13 
    14 int main()
    15 {
    16     scanf("%lld%lld%lld",&a,&b,&p);
    17     ll s=1;
    18     while(b)
    19     {
    20         if(b&1LL) s=s*a%p;
    21         a=a*a%p;
    22         b=b>>1;
    23     }
    24     printf("%lld
    ",s%p);
    25     return 0;
    26 }
    快速幂
      
     1 # include <cstdio>
     2 # include <iostream>
     3 # include <cstring>
     4 # include <string>
     5 # include <algorithm>
     6 # include <cmath>
     7 # define R register int
     8 # define ll long long
     9 
    10 using namespace std;
    11 
    12 ll a,b,p;
    13 
    14 int main()
    15 {
    16     scanf("%lld%lld%lld",&a,&b,&p);
    17     ll s=0;
    18     while(b)
    19     {
    20         if(b&1LL) s=s+a%p;
    21         a=a+a%p;
    22         b=b>>1;
    23     }
    24     printf("%lld
    ",s%p);
    25     return 0;
    26 }
    快速加
      
    1 int ad (int a,int b)
    2 {
    3     a+=b;
    4     if(a>=p) a-=p;
    5     return a;
    6 }
    加法取模优化
      
    1 inv[1]=1;
    2 for (R i=2;i<=n;++i)
    3     inv[i]=(mod-mod/i)*inv[mod%i]%mod;
    线性求逆元
      
     1 # include <cstdio>
     2 # include <iostream>
     3 # include <cstring>
     4 # include <string>
     5 # include <algorithm>
     6 # include <cmath>
     7 # define R register int
     8 # define ll long long
     9 
    10 using namespace std;
    11 
    12 const int maxn=10000007;
    13 int f[maxn],pri[maxn],h;
    14 
    15 void sieve()
    16 {
    17     f[1]=1;
    18     for (R i=2;i<=n;++i)
    19     {
    20         if(!f[i]) pri[++h]=i;
    21         for (R j=1;j<=h&&i*pri[j]<=n;++j)
    22         {
    23             f[ i*pri[j] ]=1;
    24             if(i%pri[j]==0) break;
    25         }
    26     }
    27 }
    28 
    29 int main()
    30 {
    31 
    32     return 0;
    33 }
    线性筛素数
      
    1 void sdiv (int x)
    2 {
    3     for (R i=2;i*i<=n;++i)
    4     {
    5         if(x%i==0) p[++h]=i;
    6         while(x%i==0) c[h]++,x/=i;
    7     }
    8     if(x!=1) p[h]=x,c[h]=1;
    9 }
    根号时间分解质因数
      
     1 # include <cstdio>
     2 # include <iostream>
     3 # include <cstring>
     4 # include <string>
     5 # include <algorithm>
     6 # include <cmath>
     7 # define R register int
     8 # define ll long long
     9 
    10 using namespace std;
    11 
    12 const int maxn=10000007;
    13 int f[maxn],pri[maxn],h,m[maxn],a[maxn];
    14 
    15 void ldiv (int x)
    16 {
    17     int cnt=0;
    18     while(x!=1)
    19     {
    20         a[++cnt]=m[x];
    21         x/=m[x];
    22     }
    23 }
    24 
    25 void sieve()
    26 {
    27     f[1]=1;
    28     for (R i=2;i<=n;++i)
    29     {
    30         if(!f[i]) pri[++h]=i,m[i]=i;
    31         for (R j=1;j<=h&&i*pri[j]<=n;++j)
    32         {
    33             f[ i*pri[j] ]=1;
    34             m[ i*pri[j] ]=pri[j];
    35             if(i%pri[j]==0) break;
    36         }
    37     }
    38 }
    39 
    40 int main()
    41 {
    42     sieve();
    43     return 0;
    44 }
    log时间分解质因数
      
     1 f[1]=1,phi[1]=1;
     2 for(re int i=2;i<=n;i++)
     3 {
     4     if(!f[i]) p[++p[0]]=i,phi[i]=i-1;
     5     for(re int j=1;j<=p[0]&&p[j]*i<=n;j++)
     6     {
     7         f[p[j]*i]=1;
     8         if(i%p[j]==0)
     9         {
    10             phi[p[j]*i]=phi[i]*p[j];
    11             break;
    12         }
    13         phi[p[j]*i]=phi[i]*(p[j]-1);
    14     }
    15 }
    16 这个是抄的asuldb的.
    欧拉筛
      
    1 int gcd (int a,int b) { return b?gcd(b,a%b):a; }
    gcd
      
     1 int gcd (int a,int b)
     2 {
     3     int p=1;
     4     if(a<b) swap(a,b);
     5     while(a&&b)
     6     {
     7         if(a%2==0&&b%2==0) p*=2,a/=2,b/=2;
     8         else if(a%2&&b%2==0) b/=2;
     9         else if(a%2==0&&b%2) a/=2;
    10         else a-=b;
    11         if(a<b) swap(a,b);
    12     }
    13     return p*a;
    14 }
    Stein算法求gcd
      
      1 # include <cstdio>
      2 # include <iostream>
      3 # include <cstring>
      4 # include <string>
      5 # define R register int
      6 
      7 using namespace std;
      8 
      9 const int maxn=10005;
     10 const int base=1e8;
     11 char c[maxn];
     12 struct big
     13 {
     14     int a[maxn];
     15     int len;
     16     void write()
     17     {
     18         printf("%d",a[len]);
     19         for (R i=len-1;i>=1;--i)
     20             printf("%08d",a[i]);
     21         if(len==0) printf("0");
     22     }
     23     void div()
     24     {
     25         int mod=0;
     26         for (R i=len;i>=1;--i)
     27         {
     28             a[i]+=mod*base;
     29             mod=a[i]%2;
     30             a[i]/=2;
     31         }
     32         while (a[ len ]==0&&len) len--;
     33     }
     34     void clear()
     35     {
     36         memset(a,0,sizeof(a));
     37         len=0;
     38     }
     39     void mul()
     40     {
     41         for (R i=1;i<=len;++i)
     42             a[i]*=2;
     43         for (R i=1;i<=len+1;++i)
     44             a[i+1]+=a[i]/base,a[i]%=base;
     45         len++;
     46         while (a[ len ]==0&&len) len--;
     47     }
     48     bool operator < (const big &b) const
     49     {
     50         if(b.len!=len) return len<b.len;
     51         for (R i=len;i>=1;--i)
     52             if(b.a[i]==a[i]) continue;
     53             else return a[i]<b.a[i];
     54         return false;
     55     }
     56     void read()
     57     {
     58         scanf("%s",c+1);
     59         int l=strlen(c+1);
     60         len=l/8+((l%8)?1:0);
     61         int x=0,pos=0;
     62         for (R i=1;i<=l;++i)
     63         {
     64             x=x*10+c[i]-'0';
     65             if(i%8==l%8)
     66             {
     67                 a[ len-pos ]=x;
     68                 pos++;
     69                 x=0;
     70             }
     71         }
     72         if(x) a[len-pos]=x;
     73     }
     74 }A,B;
     75 
     76 void sub()
     77 {
     78     for (R i=1;i<=B.len;++i)
     79     {
     80         A.a[i]-=B.a[i];
     81         if(A.a[i]<0) A.a[i]+=base,A.a[i+1]--;
     82     }
     83     while (A.a[ A.len ]==0&&A.len) A.len--;
     84 }
     85 
     86 void gcd ()
     87 {
     88     int cnt=0;
     89     if(A<B) swap(A,B);
     90     while (A.len&&B.len)
     91     {
     92         if(A.a[1]%2==0&&B.a[1]%2==0) cnt++,A.div(),B.div();
     93         else if (A.a[1]%2&&B.a[1]%2==0) B.div();
     94         else if (A.a[1]%2==0&&B.a[1]%2) A.div();
     95         else sub();
     96         if(A<B) swap(A,B);
     97     }
     98     for (R i=1;i<=cnt;++i)
     99         A.mul();
    100     A.write();
    101 }
    102 
    103 int main()
    104 {
    105     A.read();
    106     B.read();
    107        gcd();
    108     return 0;
    109 }
    压位高精实现Stein算法
      
     1 void exgcd (int a,int b,int &x,int &y)
     2 {
     3     if(b==0)
     4     {
     5         x=1,y=0;
     6         return;
     7     }
     8     exgcd(b,a%b,y,x);
     9     y-=a/b*x;
    10 }
    exgcd
      
     1 # include <cstdio>
     2 # include <iostream>
     3 # include <cstring>
     4 # include <string>
     5 # define R register int
     6 # define ll long long
     7 
     8 using namespace std;
     9 
    10 const int maxn=10000;
    11 int a[maxn],b[maxn];
    12 char c[maxn];
    13 
    14 int main()
    15 {
    16     scanf("%s",c+1);
    17     a[0]=strlen(c+1);
    18     for (R i=1;i<=a[0];++i)
    19         a[i]=c[ a[0]-i+1 ]-'0';
    20     scanf("%s",c+1);
    21     b[0]=strlen(c+1);
    22     for (R i=1;i<=b[0];++i)
    23         b[i]=c[ b[0]-i+1 ]-'0';
    24     a[0]=max(a[0],b[0])+1;
    25     for (R i=1;i<=a[0];++i)
    26     {
    27         a[i]+=b[i];
    28         a[i+1]+=a[i]/10;
    29         a[i]%=10;
    30     }
    31     while(a[ a[0] ]==0&&a[0]) a[0]--;
    32     for (R i=a[0];i>=1;--i)
    33         printf("%d",a[i]);
    34     if(a[0]==0) printf("0");
    35     return 0;
    36 }
    高精度加法
      
     1 # include <cstdio>
     2 # include <iostream>
     3 # include <cstring>
     4 # include <string>
     5 # define R register int
     6 # define ll long long
     7 
     8 using namespace std;
     9 
    10 const int maxn=10005;
    11 int a[maxn],b[maxn];
    12 char c[maxn];
    13 
    14 bool smaller ()
    15 {
    16     if(a[0]!=b[0]) return a[0]<b[0];
    17     for (R i=a[0];i>=1;--i)
    18         if(a[i]!=b[i]) return a[i]<b[i];
    19     return false;
    20 }
    21 
    22 void chan()
    23 {
    24     int n=max(a[0],b[0]);
    25     for (R i=0;i<=n;++i)
    26         swap(a[i],b[i]);
    27 }
    28 
    29 int main()
    30 {
    31     scanf("%s",c+1);
    32     a[0]=strlen(c+1);
    33     for (R i=1;i<=a[0];++i)
    34         a[i]=c[ a[0]-i+1 ]-'0';
    35     scanf("%s",c+1);
    36     b[0]=strlen(c+1);
    37     for (R i=1;i<=b[0];++i)
    38         b[i]=c[ b[0]-i+1 ]-'0';
    39     if(smaller())
    40     {
    41         printf("-");
    42         chan();
    43     } 
    44     for (R i=1;i<=a[0];++i)
    45     {  
    46         a[i]-=b[i];
    47         if(a[i]<0) a[i]+=10,a[i+1]--;
    48     }
    49     while(a[ a[0] ]==0&&a[0]) a[0]--;
    50     for (R i=a[0];i>=1;--i)
    51         printf("%d",a[i]);
    52     if(a[0]==0) printf("0");
    53     return 0;
    54 }
    高精度减法
      
     1 # include <cstdio>
     2 # include <iostream>
     3 # include <cstring>
     4 # include <string>
     5 # define R register int
     6 # define ll long long
     7 
     8 using namespace std;
     9 
    10 const int maxn=10005;
    11 int a[maxn],b[maxn],d[maxn];
    12 char c[maxn];
    13 
    14 int main()
    15 {
    16     scanf("%s",c+1);
    17     a[0]=strlen(c+1);
    18     for (R i=1;i<=a[0];++i)
    19         a[i]=c[ a[0]-i+1 ]-'0';
    20     scanf("%s",c+1);
    21     b[0]=strlen(c+1);
    22     for (R i=1;i<=b[0];++i)
    23         b[i]=c[ b[0]-i+1 ]-'0';
    24     d[0]=a[0]+b[0]+2;
    25     for (R i=1;i<=a[0];++i)
    26         for (R j=1;j<=b[0];++j)
    27             d[i+j-1]+=a[i]*b[j];
    28     for (R i=1;i<=d[0];++i)
    29     {
    30         d[i+1]+=d[i]/10;
    31         d[i]%=10;
    32     }
    33     while(d[ d[0] ]==0&&d[0]) d[0]--;
    34     for (R i=d[0];i>=1;--i)
    35         printf("%d",d[i]);
    36     if(d[0]==0) printf("0");
    37     return 0;
    38 }
    高精度乘法
      
     1 # include <cstdio>
     2 # include <iostream>
     3 # include <cstring>
     4 # include <string>
     5 # include <algorithm>
     6 # include <cmath>
     7 # include <map>
     8 # define R register int
     9 # define ll long long
    10 
    11 using namespace std;
    12 
    13 const int maxn=100000;
    14 int T,n,m,a[maxn],sta[maxn],Top;
    15 char c[maxn];
    16 map <char,int> m1;
    17 map <int,char> m2;
    18 
    19 int main() //模m取余,逆序输出,除法退位位时注意上一位的余数乘n即可 
    20 {
    21     scanf("%d",&T);
    22     for (R i=0;i<=9;++i)
    23         m1[ i+'0' ]=i,m2[i]=i+'0';
    24     for (R i=10;i<=35;++i)
    25         m1[i-10+'A']=i,m2[i]=i-10+'A';
    26     for (R i=36;i<=61;++i)
    27         m1[i-36+'a']=i,m2[i]=i-36+'a';
    28     while (T--)
    29     {
    30         scanf("%d%d",&n,&m);
    31         scanf("%s",c+1);
    32         a[0]=strlen(c+1);
    33         Top=0;
    34         for (R i=1;i<=a[0];++i)
    35             a[a[0]-i+1]=m1[ c[i] ];
    36         printf("%d ",n);
    37         for (R i=a[0];i>=1;--i)
    38             printf("%c",m2[ a[i] ]);
    39         printf("
    ");
    40         while(a[0])
    41         {
    42             int r=0;
    43             for (R i=a[0];i>=1;--i)
    44             {
    45                 a[i]=r*n+a[i];
    46                 r=a[i]%m;
    47                 a[i]/=m;
    48             }
    49             sta[++Top]=r;
    50             while(a[ a[0] ]==0&&a[0]) a[0]--;
    51         }
    52         printf("%d ",m);
    53         for (R i=Top;i>=1;--i)
    54             printf("%c",m2[ sta[i] ]);
    55         printf("
    
    ");
    56     }
    57 }
    高精度n进制转m进制
      
     1 # include <cstdio>
     2 # include <iostream>
     3 # include <cstring>
     4 # include <string>
     5 # define R register int
     6 # define ll long long
     7 
     8 using namespace std;
     9 
    10 const int maxn=10005;
    11 int a[maxn],b;
    12 char c[maxn];
    13 
    14 int main()
    15 {
    16     scanf("%s",c+1);
    17     a[0]=strlen(c+1);
    18     for (R i=1;i<=a[0];++i)
    19         a[i]=c[ a[0]-i+1 ]-'0';
    20     scanf("%d",&b);
    21     ll r=0;
    22     for (R i=a[0];i>=1;--i)
    23     {
    24         a[i]+=r*10;
    25         r=a[i]%b;
    26         a[i]/=b;
    27     }
    28     while(a[ a[0] ]==0&&a[0]) a[0]--;
    29     for (R i=a[0];i>=1;--i)
    30         printf("%d",a[i]);
    31     if(a[0]==0) printf("0");
    32     printf("
    %lld",r);
    33     return 0;
    34 }
    高精度除法+取模
      
     1 # include <cstdio>
     2 # include <iostream>
     3 # include <cstring>
     4 # include <string>
     5 # include <algorithm>
     6 # include <cmath>
     7 # define R register int
     8 # define ll long long
     9 
    10 using namespace std;
    11 
    12 int T;
    13 ll f[100005],inv[100005];
    14 ll n,m,p;
    15 
    16 ll c(ll n,ll m)
    17 {
    18     if(n<m) return 0;  
    19     return (f[n]*inv[m]%p)*inv[n-m]%p;
    20 }
    21 
    22 ll lucas(ll n,ll m)
    23 {
    24     if(m==0)
    25         return 1;
    26     else
    27         return (ll)lucas(n/p,m/p)*c(n%p,m%p)%p;
    28 }
    29 
    30 ll quick_pow(ll x,ll c)
    31 {
    32     ll s=1;
    33     while (c)
    34     {
    35         if(c&1) s=s*x%p;
    36         x=x*x%p;
    37         c=c>>1;
    38     }
    39     return s%p;
    40 }
    41 
    42 void init()
    43 {
    44     f[0]=inv[0]=1;
    45     for (int i=1;i<p;++i)
    46     {
    47         f[i]=f[i-1]*i%p;
    48         inv[i]=quick_pow(f[i],p-2);
    49     }
    50 }
    51 
    52 int main()
    53 {
    54     scanf("%d",&T);
    55     while (T--)
    56     {
    57         scanf("%lld%lld%lld",&n,&m,&p);
    58         init();
    59         printf("%lld
    ",lucas(n+m,m));
    60     }
    61     return 0;
    62 }
    Lucas
      
      1 # include <cstdio>
      2 # include <iostream>
      3 # define R register int
      4 # define ll long long
      5 
      6 using namespace std;
      7 
      8 ll n,m,p;
      9 int h;
     10 ll a[12];
     11 ll pr[12],po[12];
     12 ll ans=1;
     13 
     14 ll qui (ll a,ll b,ll p)
     15 {
     16     ll s=1;
     17     while (b)
     18     {
     19         if(b&1LL) s=s*a%p;
     20         a=a*a%p;
     21         b=b>>1LL;
     22     }
     23     return s;
     24 }
     25 
     26 void ex_gcd (ll a,ll b,ll &x,ll &y)
     27 {
     28     if(!b) { x=1LL,y=0LL; return ; }
     29     ex_gcd(b,a%b,y,x);
     30     y-=a/b*x;
     31 }
     32 
     33 ll inv (ll a,ll p)
     34 {
     35     ll x,y;
     36     ex_gcd(a,p,x,y);
     37     return (x%p+p)%p;
     38 }
     39 
     40 ll crt ()
     41 {
     42     ll ans=0;
     43     ll x,y,m,pri;
     44     for (R i=1;i<=h;++i)
     45     {
     46         pri=po[i];
     47         m=p/pri;
     48         m%=pri;
     49         ex_gcd(m,pri,x,y);
     50         x=(x%pri+pri)%pri;
     51         m=p/pri;
     52         x=x*m%p;
     53         ans=(ans+x*a[i])%p;
     54     }
     55     return ans;
     56 }
     57 
     58 ll fac (ll n,ll Pr,ll Po)
     59 {
     60     if(n==0) return 1;
     61     ll ans=1;
     62     for (R i=2;i<=Po;++i)
     63         if(i%Pr) ans=ans*i%Po;
     64     ans=qui(ans,n/Po,Po);
     65     for (R i=2;i<=n%Po;++i)
     66         if(i%Pr) ans=ans*i%Po;
     67     return ans*fac(n/Pr,Pr,Po)%Po;
     68     
     69 }
     70 
     71 ll C (ll n,ll m,ll Pr,ll Po)
     72 {
     73     if(m>n) return 0;
     74     ll t=0;
     75     ll a=fac(n,Pr,Po),b=fac(m,Pr,Po),c=fac(n-m,Pr,Po);
     76     for (ll i=n;i;i/=Pr) t+=i/Pr;
     77     for (ll i=m;i;i/=Pr) t-=i/Pr;
     78     for (ll i=n-m;i;i/=Pr) t-=i/Pr;
     79     return qui(Pr,t,Po)*a*inv(b,Po)%Po*inv(c,Po)%Po;
     80 }
     81 
     82 
     83 ll Lucas (ll n,ll m)
     84 {
     85     for (R i=1;i<=h;++i)
     86         a[i]=C(n,m,pr[i],po[i])%p;
     87     return crt();
     88 }
     89 
     90 void div (ll p)
     91 {
     92     for (R i=2;i*i<=p;++i)
     93     {
     94         if(p%i==0)
     95         {
     96             ++h;
     97             pr[h]=i;
     98             po[h]=1;
     99             while (p%i==0) po[h]*=i,p/=i;
    100         }
    101     }
    102     if(p>1) pr[++h]=p,po[h]=p;
    103 }
    104 
    105 int main()
    106 {
    107     scanf("%lld%lld",&n,&m);
    108     scanf("%lld",&p),div(p);
    109     printf("%lld",Lucas(n,m));
    110     return 0;
    111 }
    Exlucas
      
     1 # include <cstdio>
     2 # include <iostream>
     3 # define ll long long
     4 # define R register int
     5 
     6 using namespace std;
     7 
     8 const int maxn=100005;
     9 int n,f;
    10 ll m[maxn],c[maxn],m1,m2,c1,c2,I,g,x,y;
    11 
    12 inline char gc() {
    13     static char buf[100000],*p1,*p2;
    14     return p1==p2&&(p2=(p1=buf)+fread(buf,1,100000,stdin),p1==p2)?EOF:*p1++;
    15 }
    16 ll read() {
    17     ll x=0; 
    18     char c=gc();
    19     while(!isdigit(c)) c=gc();
    20     while(isdigit(c)) x=(x<<3)+(x<<1)+(c^48),c=gc();
    21     return x;
    22 }
    23 
    24 ll gcd (ll a,ll b) { return b?gcd(b,a%b):a; }
    25 void exgcd (ll a,ll b,ll &x,ll &y)
    26 {
    27     if(b==0)
    28     {
    29         x=1,y=0;
    30         return ;
    31     }
    32     exgcd(b,a%b,y,x);
    33     y-=a/b*x;
    34 }
    35 ll inv (ll a,ll b)
    36 {
    37     ll x,y;
    38     exgcd(a,b,x,y);
    39     x=(x%b+b)%b;
    40     if(!x) x+=b;
    41     return x;
    42 }
    43 
    44 ll mul (ll a,ll b,ll p)
    45 {
    46     ll s=0;
    47     a=(a%p+p)%p;
    48     b=(b%p+p)%p;
    49     while (b)
    50     {
    51         if(b&1LL) s=(s+a)%p;
    52         a=(a+a)%p;
    53         b=b>>1LL;
    54     }
    55     return s%p;
    56 }
    57 
    58 int main()
    59 {
    60     scanf("%d",&n);
    61     f=0;
    62     for (R i=1;i<=n;++i)
    63         m[i]=read(),c[i]=read();
    64     for (R i=2;i<=n;++i)
    65     {
    66         m1=m[1],m2=m[i],c1=c[1],c2=c[i];
    67         exgcd(m1,m2,x,y);
    68         g=gcd(m1,m2);
    69         ll t=m[i]/g;
    70         x=mul(x,(c2-c1)/g,t);
    71         x=(x%t+t)%t;
    72         c[1]=(c[1]+mul(m[1],x,m[1]*t))%(m[1]*t);
    73         m[1]*=t;
    74         
    75     }
    76     printf("%lld",(c[1]%m[1]+m[1])%m[1]);
    77     return 0;
    78 }
    Excrt

    数据结构

      
     1 # include <cstdio>
     2 # include <iostream>
     3 # define R register int
     4 
     5 using namespace std;
     6 
     7 int c[500005]={0},n;
     8 
     9 void add (int x,int v) 
    10 {
    11     for (R i=x;i<=n;i+=(i&(-i))) c[i]+=v;
    12 }
    13 
    14 int ask (int x)
    15 {
    16     int S=0;
    17     for (R i=x;i;i-=(i&(-i))) S+=c[i];
    18     return S;
    19 }
    20 
    21 int main()
    22 {
    23     int m,x,a,b,v;
    24     scanf("%d%d",&n,&m);
    25     for (R i=1;i<=n;i++)
    26     {
    27         scanf("%d",&v);
    28         add(i,v); 
    29     }
    30     for (R i=1;i<=m;i++)
    31     {
    32         scanf("%d%d%d",&x,&a,&b);
    33         if(x==1)
    34             add(a,b);
    35         if(x==2)
    36             printf("%d
    ",ask(b)-ask(a-1));
    37     }
    38     return 0; 
    39 }
    树状数组单点加区间求和
      
     1 # include <cstdio>
     2 # include <iostream>
     3 # include <cstring>
     4 # include <string>
     5 # include <algorithm>
     6 # include <cmath>
     7 # define R register int
     8 # define ll long long
     9 
    10 using namespace std;
    11 
    12 int n,m,x,y;
    13 ll k,now,last=0;
    14 ll t[500005]={0};
    15 ll S=0;
    16 int xx;
    17 
    18 void add (int x,ll y)
    19 {
    20     for (R i=x;i<=n;i+=(i&(-i))) t[i]+=y;
    21 }
    22 
    23 ll ask (int x)
    24 {
    25     ll S=0;
    26     for (R i=x;i;i-=(i&(-i))) S+=t[i];
    27     return S;
    28 }
    29 
    30 int main()
    31 {
    32     scanf("%d%d",&n,&m);
    33     for (int i=1;i<=n;i++)
    34     {
    35         scanf("%lld",&now);
    36         add(i,now-last);
    37         last=now;
    38     }
    39     for (int i=1;i<=m;i++)
    40     {
    41         scanf("%d",&xx);
    42         if(xx==1)
    43         {
    44             scanf("%d%d",&x,&y);
    45             scanf("%lld",&k);
    46             add(x,k);
    47             add(y+1,-k);    
    48         }
    49         if (xx==2)
    50         {
    51             scanf("%d",&x);
    52             printf("%lld
    ",ask(x));
    53         }
    54     }
    55     return 0;
    56 }
    树状数组区间加单点查询
      
     1 # include <cstdio>
     2 # include <iostream>
     3 # include <cstring>
     4 # include <string>
     5 # include <algorithm>
     6 # include <cmath>
     7 # define R register int
     8 # define ll long long
     9 
    10 using namespace std;
    11 
    12 int m,n,op,x,y,opt;
    13 ll a[100004]={0},k,s1,s2;
    14 ll c[100004]={0},c1[100004]={0};
    15 
    16 void add (ll *t,int pos,ll v)
    17 {
    18     for (R i=pos;i<=n;i+=(i&(-i)))
    19         t[i]+=v;
    20 }
    21 
    22 ll ask (ll *t,int pos)
    23 {
    24     ll ans=0;
    25     for (R i=pos;i;i-=(i&(-i)))
    26         ans+=t[i];
    27     return ans;
    28 }
    29 
    30 int main()
    31 {
    32     scanf("%d%d",&n,&m);
    33     for (R i=1;i<=n;++i)
    34     {
    35         scanf("%lld",&a[i]);
    36         add(c,i,a[i]-a[i-1]);
    37         add(c1,i,(i-1)*(a[i]-a[i-1]));
    38     }
    39     for (R i=1;i<=m;++i)
    40     {
    41         scanf("%d",&opt);
    42         if (op==1) 
    43         {
    44             scanf("%d%d%lld",&x,&y,&k);
    45             add(c,x,k);
    46             add(c,y+1,-k);
    47             add(c1,x,k*(x-1));
    48             add(c1,y+1,-k*y);
    49         }
    50         if (op==2)
    51         {
    52             scanf("%d%d",&x,&y);
    53             s1=(x-1)*ask(c,x-1)-ask(c1,x-1);
    54             s2=y*ask(c,y)-ask(c1,y);
    55             printf("%lld
    ",s2-s1);
    56         }
    57     }
    58     return 0;
    59 }
    树状数组区间加区间查询
      
     1 # include <cstdio>
     2 # include <iostream>
     3 # include <cstring>
     4 # define R register int
     5 # define lowbit(x) (x&(-x))
     6 
     7 using namespace std;
     8 
     9 const int maxn=2050;
    10 int a,b,c,d,n,m,s1,s2,s3,s4,v;
    11 string st;
    12 int c1[maxn][maxn],c2[maxn][maxn],c3[maxn][maxn],c4[maxn][maxn];
    13 
    14 inline void add(int x,int y,int v)
    15 {
    16     for (R i=x;i<=n;i+=lowbit(i))
    17         for (R j=y;j<=m;j+=lowbit(j))
    18         {
    19             c1[i][j]+=v;
    20             c2[i][j]+=v*x;
    21             c3[i][j]+=v*y;
    22             c4[i][j]+=v*x*y;
    23         }
    24 }
    25 
    26 inline int ask(int x,int y)
    27 {
    28     int ans=0;
    29     for (R i=x;i;i-=lowbit(i))
    30         for (R j=y;j;j-=lowbit(j))
    31         {
    32             ans+=(x+1)*(y+1)*c1[i][j];
    33             ans-=(y+1)*c2[i][j];
    34             ans-=(x+1)*c3[i][j];
    35             ans+=c4[i][j];
    36         }
    37     return ans;
    38 }
    39 
    40 int main()
    41 {
    42     scanf("X %d %d",&n,&m);
    43     while (cin>>st)
    44     {
    45         if(st[0]=='L') scanf("%d%d%d%d%d",&a,&b,&c,&d,&v);
    46         else    scanf("%d%d%d%d",&a,&b,&c,&d);
    47         if(st[0]=='L')
    48         {
    49             add(a,b,v);
    50             add(a,d+1,-v);
    51             add(c+1,b,-v);
    52             add(c+1,d+1,v);
    53         }
    54         else
    55             printf("%d
    ",ask(c,d)-ask(c,b-1)-ask(a-1,d)+ask(a-1,b-1));
    56     }
    57     return 0;
    58 }
    二维树状数组区间加区间查询
      
     1 # include <cstdio>
     2 # include <iostream>
     3 # include <cstring>
     4 # include <string>
     5 # include <algorithm>
     6 # include <cmath>
     7 # define R register int
     8 # define LL long long
     9 # define nl (n<<1)
    10 # define nr (n<<1|1)
    11 
    12 using namespace std;
    13 
    14 const int maxn=100005;
    15 int n,m,opt,x,y;
    16 LL k,t[maxn<<2],delta[maxn<<2];
    17 
    18 void pushdown (int n,int l,int r)
    19 {
    20     int mid=(l+r)>>1;
    21     LL x=delta[n];
    22     delta[nl]+=x;
    23     delta[nr]+=x;
    24     delta[n]=0;
    25     t[nl]+=(mid-l+1)*x;
    26     t[nr]+=(r-mid)*x;
    27 }
    28 
    29 void build (int n,int l,int r)
    30 {
    31     if(l==r)
    32     {
    33         scanf("%lld",&t[n]);
    34         return;
    35     }
    36     int mid=(l+r)>>1;
    37     build(nl,l,mid);
    38     build(nr,mid+1,r);
    39     t[n]=t[nl]+t[nr];
    40 }
    41 
    42 void add (int n,int l,int r,int ll,int rr,LL v)
    43 {
    44     if(ll<=l&&r<=rr)
    45     {
    46         delta[n]+=v;
    47         t[n]+=(r-l+1)*v;
    48         return;
    49     }
    50     int mid=(l+r)>>1;
    51     if(delta[n]) pushdown(n,l,r);
    52     if(ll<=mid) add(nl,l,mid,ll,rr,v);
    53     if(rr>mid)  add(nr,mid+1,r,ll,rr,v);
    54     t[n]=t[nl]+t[nr];
    55 }
    56 
    57 LL ask (int n,int l,int r,int ll,int rr)
    58 {
    59     if(ll<=l&&r<=rr)
    60         return t[n];
    61     if(delta[n]) pushdown(n,l,r);
    62     int mid=(l+r)>>1;
    63     LL ans=0;
    64     if(ll<=mid) ans=ans+ask(nl,l,mid,ll,rr);
    65     if(rr>mid)  ans=ans+ask(nr,mid+1,r,ll,rr);
    66     return ans;
    67 }
    68 
    69 int main()
    70 {
    71     scanf("%d%d",&n,&m);
    72     build(1,1,n);
    73     for (R i=1;i<=m;++i)
    74     {
    75         scanf("%d",&opt);
    76         if(opt==1)
    77         {
    78             scanf("%d%d%lld",&x,&y,&k);
    79             add(1,1,n,x,y,k);
    80         }
    81         else
    82         {
    83             scanf("%d%d",&x,&y);
    84             printf("%lld
    ",ask(1,1,n,x,y));
    85         }
    86     }
    87     return 0;
    88 }
    线段树区间加区间求和
      
      1 # include <cstdio>
      2 # include <iostream>
      3 # include <cstring>
      4 # include <string>
      5 # include <algorithm>
      6 # include <cmath>
      7 # define R register int
      8 # define nl (n<<1)
      9 # define nr (n<<1|1)
     10 
     11 using namespace std;
     12 
     13 const int maxn=100005;
     14 int z,x,y,n,m,r,p,a[maxn],h,firs[maxn],dep[maxn],f[maxn],siz[maxn],son[maxn],id[maxn];
     15 int cnt,top[maxn],c[maxn],t[maxn<<2],delta[maxn<<2];
     16 struct edge
     17 {
     18     int too,nex;
     19 }g[maxn<<1];
     20 
     21 int read ()
     22 {
     23     int x=0,f=1;
     24     char c=getchar();
     25     while (!isdigit(c)) { if(c=='-') f=-f; c=getchar(); }
     26     while (isdigit(c)) x=(x<<3)+(x<<1)+(c^48),c=getchar();
     27     return x*f;
     28 }
     29 
     30 void add_ed (int x,int y)
     31 {
     32     g[++h].nex=firs[x];
     33     g[h].too=y;
     34     firs[x]=h;
     35 }
     36 
     37 void dfs1 (int x)
     38 {
     39     siz[x]=1;
     40     int j,maxx=0;
     41     for (R i=firs[x];i;i=g[i].nex)
     42     {
     43         j=g[i].too;
     44         if(dep[j]) continue;
     45         dep[j]=dep[x]+1;
     46         dfs1(j);
     47         f[j]=x;
     48         siz[x]+=siz[j];
     49         if(siz[j]>maxx) maxx=siz[j],son[x]=j;
     50     }
     51 }
     52 
     53 void dfs2 (int x,int Tp)
     54 {
     55     int j;
     56     id[x]=++cnt;
     57     c[cnt]=a[x];
     58     top[x]=Tp;
     59     if(!son[x]) return;
     60     dfs2(son[x],Tp);
     61     for (R i=firs[x];i;i=g[i].nex)
     62     {
     63         j=g[i].too;
     64         if(j==f[x]||j==son[x]) continue;
     65         dfs2(j,j);
     66     }
     67 }
     68 
     69 void build (int n,int l,int r)
     70 {
     71     if(l==r)
     72         t[n]=c[l]%p;
     73     else
     74     {
     75         int mid=(l+r)>>1;
     76         build(nl,l,mid);
     77         build(nr,mid+1,r);
     78         t[n]=(t[nl]+t[nr])%p;
     79     }
     80 }
     81 
     82 void pushdown (int n,int l,int r)
     83 {
     84     int mid=(l+r)>>1,x=delta[n];
     85     delta[n]=0;
     86     delta[nl]+=x;
     87     delta[nr]+=x;
     88     t[nl]=(t[nl]+1LL*x*(mid-l+1)%p)%p;
     89     t[nr]=(t[nr]+1LL*x*(r-mid)%p)%p;
     90 }
     91 
     92 void add (int n,int l,int r,int ll,int rr,int z)
     93 {
     94     if(ll<=l&&r<=rr)
     95     {
     96         delta[n]+=z;
     97         t[n]=(t[n]+1LL*z*(r-l+1)%p)%p;
     98         return;
     99     }
    100     int mid=(l+r)>>1;
    101     if(delta[n]) pushdown(n,l,r);
    102     if(ll<=mid) add(nl,l,mid,ll,rr,z);
    103     if(rr>mid) add(nr,mid+1,r,ll,rr,z);
    104     t[n]=(t[nl]+t[nr])%p;
    105 }
    106 
    107 int ask (int n,int l,int r,int ll,int rr)
    108 {
    109     if(ll<=l&&r<=rr) return t[n];
    110     int mid=(l+r)>>1,ans=0;
    111     if(delta[n]) pushdown(n,l,r);
    112     if(ll<=mid) ans=(ans+ask(nl,l,mid,ll,rr))%p;
    113     if(rr>mid) ans=(ans+ask(nr,mid+1,r,ll,rr))%p;
    114     return ans;
    115 }
    116 
    117 void add_link (int x,int y,int z)
    118 {
    119     z%=p;
    120     while(top[x]!=top[y])
    121     {
    122         if(dep[ top[x] ]>dep[ top[y] ]) swap(x,y);
    123         add(1,1,n,id[ top[y] ],id[y],z);
    124         y=f[ top[y] ];
    125     }
    126     if(dep[x]>dep[y]) swap(x,y);
    127     add(1,1,n,id[x],id[y],z);
    128 }
    129 
    130 int ask_link (int x,int y)
    131 {
    132     int ans=0;
    133     while(top[x]!=top[y])
    134     {
    135         if(dep[ top[x] ]>dep[ top[y] ]) swap(x,y);
    136         ans=(ans+ask(1,1,n,id[ top[y] ],id[y]))%p;
    137         y=f[ top[y] ];
    138     }
    139     if(dep[x]>dep[y]) swap(x,y);
    140     ans=(ans+ask(1,1,n,id[x],id[y]))%p;
    141     return ans;
    142 }
    143 
    144 void add_st (int x,int z)
    145 {
    146     z%=p;
    147     add(1,1,n,id[x],id[x]+siz[x]-1,z);
    148 }
    149 
    150 int ask_st (int x)
    151 {
    152     return ask(1,1,n,id[x],id[x]+siz[x]-1);
    153 }
    154 
    155 int main()
    156 {
    157     n=read(),m=read(),r=read(),p=read();
    158     for (R i=1;i<=n;++i) a[i]=read();
    159     for (R i=1;i<n;++i)
    160     {
    161         scanf("%d%d",&x,&y);
    162         add_ed(x,y);
    163         add_ed(y,x);
    164     }
    165     dep[r]=1;
    166     dfs1(r);
    167     dfs2(r,r);
    168     build(1,1,n);
    169     for (R i=1;i<=m;++i)
    170     {
    171         int opt=read();
    172         if(opt==1)
    173         {
    174             x=read(),y=read(),z=read();
    175             add_link(x,y,z);
    176         }
    177         else if(opt==2)
    178         {
    179             x=read(),y=read();
    180             printf("%d
    ",ask_link(x,y));
    181         }
    182         else if(opt==3)
    183         {
    184             x=read(),y=read();
    185             add_st(x,y);
    186         }
    187         else 
    188     {
    189         x=read();
    190         printf("%d
    ",ask_st(x));
    191         }
    192     }
    193     return 0;
    194 }
    树链剖分
      
     1 #include <cstdio>
     2 #include <iostream>
     3 #include <cstring>
     4 #include <string>
     5 #include <algorithm>
     6 #include <cmath>
     7 #define R register int
     8 #define ll long long
     9 
    10 using namespace std;
    11 
    12 const int maxn=100;
    13 int f[maxn]={0},z[maxn],n;
    14 
    15 int father(int x)
    16 {
    17     if (f[x]!=x) return f[x]=father(f[x]);
    18     return x;
    19 }
    20 
    21 void Union(int x, int y)
    22 {
    23     x=f(x);
    24     y=ff(y);
    25     if (x==y) return;
    26     if(z[x]>z[y]) z[x]+=z[y],f[y]=x;
    27     else z[y]+=z[x],f[x]=y;
    28 }
    29 
    30 void init()
    31 {
    32     for (int i = 1; i <= n; i++)
    33         f[i]=i,z[i]=1;
    34 }
    35 
    36 int main()
    37 {
    38     scanf("%d", &n);
    39     init();
    40     return 0;
    41 }
    并查集
      
      1 # include <cstdio>
      2 # include <iostream>
      3 # include <cstring>
      4 # include <string>
      5 # include <algorithm>
      6 # include <cmath>
      7 # include <cstdlib>
      8 # define R register int
      9 # define ll long long
     10 # define inf 100000008
     11 
     12 using namespace std;
     13 
     14 const int maxn=100005;
     15 int n,opt,x;
     16 struct node
     17 {
     18     int n,r,s,v;
     19     node *ch[2];
     20     void in (int x)
     21     {
     22         n=s=1;
     23         v=x;
     24         r=rand();
     25         ch[0]=ch[1]=NULL;
     26     }
     27     void update ()
     28     {
     29         s=n;
     30         if(ch[0]) s+=ch[0]->s;
     31         if(ch[1]) s+=ch[1]->s;
     32     }
     33     int cmp (int x)
     34     {
     35         if(x==v) return -1;
     36         return x>v;
     37     }
     38 }*roo,pool[maxn];
     39 
     40 node *newnode ()
     41 {
     42     static int cnt=0;
     43     return &pool[++cnt];
     44 }
     45 
     46 void rotate (node *&n,int d)
     47 {
     48     node *k=n->ch[d];
     49     n->ch[d]=k->ch[d^1];
     50     k->ch[d^1]=n;
     51     n->update();
     52     k->update();
     53     n=k;
     54 }
     55 
     56 void ins (node *&n,int x)
     57 {
     58     if(!n) n=newnode(),n->in(x);    
     59     else
     60     {
     61         int d=n->cmp(x);
     62         if(d==-1) n->n++;        
     63         else
     64         {
     65             ins(n->ch[d],x);
     66             if(n->ch[d]->r > n->r) rotate(n,d);
     67         }
     68         n->update();
     69     }
     70 }
     71 
     72 void del (node *&n,int x)
     73 {
     74     if(!n) return;
     75     int d=n->cmp(x);
     76     if(d==-1)
     77     {
     78         if(n->n > 1) --n->n;
     79         else if(!n->ch[1]) n=n->ch[0];
     80         else if(!n->ch[0]) n=n->ch[1];    
     81         else
     82         {
     83             int f=(n->ch[0]->r > n->ch[1]->r)?0:1;
     84             rotate(n,f);
     85             del(n->ch[f^1],x);
     86         }
     87         
     88     }else del(n->ch[d],x);
     89     if(n) n->update();
     90 }
     91 
     92 int ask_key (node *&n,int x)
     93 {
     94     if(!n) return 1;
     95     if(n->v==x) return (n->ch[0]?n->ch[0]->s:0)+1;
     96     if(n->v<x) return (n->ch[0]?n->ch[0]->s:0)+n->n+ask_key(n->ch[1],x);
     97     return ask_key(n->ch[0],x);
     98 }
     99 
    100 int ask_value (node *&n,int x)
    101 {
    102     if(!n||n->s<x||x<=0) return 0;
    103     int s=n->ch[0]?n->ch[0]->s:0;
    104     if(s<x&&x<=s+n->n) return n->v;
    105     if(s>=x) return ask_value(n->ch[0],x);
    106     return ask_value(n->ch[1],x-s-n->n);
    107 }
    108 
    109 int lef (node *&n,int x)
    110 {
    111     if(!n) return -inf;
    112     if(n->v >= x) return lef(n->ch[0],x);
    113     return max(n->v,lef(n->ch[1],x)); 
    114 }
    115 
    116 int rig (node *&n,int x)
    117 {
    118     if(!n) return inf;
    119     if (n->v <= x) return rig(n->ch[1], x);
    120     return min(n->v,rig(n->ch[0], x));
    121 }
    122 
    123 int main()
    124 {
    125     scanf("%d",&n);
    126     for (R i=1;i<=n;++i)
    127     {
    128         scanf("%d%d",&opt,&x);
    129         if(opt==1) ins(roo,x);
    130         else if(opt==2) del(roo,x);
    131         else if(opt==3) printf("%d
    ",ask_key(roo,x));
    132         else if(opt==4) printf("%d
    ",ask_value(roo,x));
    133         else if(opt==5) printf("%d
    ",lef(roo,x));
    134         else printf("%d
    ",rig(roo,x));
    135     }
    136     return 0;
    137 }
    Treap
      
      1 # include <cstdio>
      2 # include <iostream>
      3 # include <queue>
      4 # include <cstring>
      5 # include <string>
      6 # define R register int
      7 # define ll long long
      8 
      9 using namespace std;
     10 
     11 const int maxn=100005;
     12 int n,m,x,y,roo;
     13 struct node
     14 {
     15     int delta,ch[2],f,siz;
     16 }t[maxn];
     17 
     18 int read();
     19 
     20 inline void update (int id)
     21 {
     22     t[id].siz=t[ t[id].ch[0] ].siz+t[ t[id].ch[1] ].siz+1;
     23 }
     24 
     25 inline void lin (int x,int f,int d)
     26 {
     27     t[x].f=f;
     28     t[f].ch[d]=x;
     29 }
     30 
     31 int build (int l,int r)
     32 {
     33     if(l>r) return 0;
     34     int mid=(l+r)>>1;
     35     lin(build(l,mid-1),mid,0);
     36     lin(build(mid+1,r),mid,1);
     37     t[mid].delta=0;
     38     update(mid);
     39     return mid;
     40 }
     41 
     42 inline void pushdown (int n)
     43 {
     44     t[n].delta=0;
     45     t[ t[n].ch[0] ].delta^=1;
     46     t[ t[n].ch[1] ].delta^=1;
     47     swap(t[n].ch[0],t[n].ch[1]);
     48 }
     49 
     50 void write (int x)
     51 {
     52     if(!x) return;
     53     if(t[x].delta) pushdown(x);
     54     write(t[x].ch[0]);
     55     if(x!=1&&x!=n+2) printf("%d ",x-1);
     56     write(t[x].ch[1]);
     57 }
     58 
     59 inline int D (int x)
     60 {
     61     return x==t[ t[x].f ].ch[1];
     62 }
     63 
     64 void rotate (int x)
     65 {
     66     int f=t[x].f;
     67     if(f==roo) roo=x;
     68     int g=t[f].f;
     69     int mf=D(x),gf=D(f);
     70     int k=t[x].ch[mf^1];
     71     lin(k,f,mf),lin(f,x,mf^1),lin(x,g,gf);
     72     update(f),update(x);
     73 }
     74 
     75 void splay (int x,int g)
     76 {
     77     while(t[x].f!=g)
     78     {
     79         if(t[ t[x].f ].f==g) rotate(x);
     80         else if(D(x)==D(t[x].f)) rotate(t[x].f),rotate(x);
     81         else rotate(x),rotate(x);
     82     }
     83     update(x);
     84 }
     85 
     86 inline int find (int x)
     87 {
     88     int no=roo;
     89     x--;
     90     if(t[no].delta) pushdown(no);
     91     while (t[ t[no].ch[0] ].siz!=x)
     92     {
     93         if(t[ t[no].ch[0] ].siz<x)
     94             x-=t[ t[no].ch[0] ].siz+1,no=t[no].ch[1];
     95         else no=t[no].ch[0];
     96         if(t[no].delta) pushdown(no);
     97     }
     98     return no;
     99 }
    100 
    101 int main()
    102 {
    103     n=read(),m=read();
    104     roo=build(1,n+2);
    105     while(m--)
    106     {
    107         x=read(),y=read();
    108         x=find(x);
    109         splay(x,0);
    110         y=find(y+2);
    111         splay(y,roo);
    112         t[ t[y].ch[0] ].delta^=1;
    113     }
    114     write(roo);
    115     return 0;
    116 }
    117 
    118 inline int read()
    119 {
    120     int x=0;
    121     char c=getchar();
    122     while (!isdigit(c)) c=getchar();
    123     while (isdigit(c)) x=(x<<3)+(x<<1)+(c^48),c=getchar();
    124     return x;
    125 }
    Splay
      
      1 # include <cstdio>
      2 # include <iostream>
      3 # include <cstring>
      4 # include <string>
      5 # include <algorithm>
      6 # include <cmath>
      7 # include <cstdlib>
      8 # include <queue>
      9 # include <ctime>
     10 # define R register int
     11 # define ll long long
     12 
     13 using namespace std;
     14 
     15 const int maxn=100005;
     16 int n,m,v[maxn],h,f[maxn],x,y,k,Q,pos[maxn];
     17 char s[2];
     18 struct node
     19 {
     20     int n,v,s,r;
     21     node *ch[2];
     22     void in (int x)
     23     {
     24         n=s=1;
     25         v=x;
     26         r=rand();
     27         ch[0]=ch[1]=NULL;
     28     }
     29     int cmp (int x)
     30     {
     31         if(x==v) return -1;
     32         return x>v;
     33     }
     34     void update()
     35     {
     36         s=n;
     37         if(ch[0]) s+=ch[0]->s;
     38         if(ch[1]) s+=ch[1]->s;
     39     }
     40 }*roo[maxn],pool[maxn*50];
     41 node *q[maxn];
     42 
     43 inline int read();
     44 node *newnode();
     45 void ins (node *&node,int x);
     46 inline void mer (int x,int y);
     47 void rotate (node *&n,int d);
     48 int father (int x);
     49 int ask (node *&n,int k);
     50 
     51 void write (int x)
     52 {
     53     if(x<0) putchar('-'),write(-x);
     54     else
     55     {
     56         if(x>=10) write(x/10);
     57         putchar(x%10+'0');
     58     }
     59 }
     60 
     61 int main()
     62 {
     63     srand(time(0));
     64     n=read(),m=read();
     65     for (R i=1;i<=n;++i)
     66         x=read(),f[i]=i,ins(roo[i],x),pos[x]=i;
     67     for (R i=1;i<=m;++i)
     68     {
     69         x=read(),y=read();
     70         if(x==0||y==0) continue;
     71         mer(x,y);
     72     }
     73     Q=read();
     74     int ans=0;
     75     while (Q--)
     76     {
     77         scanf("%s",s);
     78         x=read(),y=read();
     79         if(s[0]=='Q')
     80         {
     81             
     82             x=father(x);
     83             if(roo[x]->s<y) ans=-1;
     84             else ans=pos[ ask(roo[x],y) ];
     85             write(ans);
     86             putchar('
    ');
     87         }
     88         else
     89         {
     90             mer(x,y);
     91             if(x==0||y==0) continue;
     92         }
     93     }
     94     return 0;
     95 }
     96 
     97 inline int read()
     98 {
     99     int x=0;
    100     char c=getchar();
    101     while(!isdigit(c)) c=getchar();
    102     while(isdigit(c)) x=(x<<3)+(x<<1)+(c^48),c=getchar();
    103     return x;
    104 }
    105 
    106 int father (int x) { if(x!=f[x]) return f[x]=father(f[x]); return x; }
    107 
    108 node *newnode()
    109 {
    110     static int cnt=0;
    111     return &pool[++cnt];
    112 }
    113 
    114 void ins (node *&n,int x)
    115 {
    116     if(!n) n=newnode(),n->in(x);
    117     else
    118     {
    119         int d=n->cmp(x);
    120         if(d==-1) ++n->n;
    121         else
    122         {
    123             ins(n->ch[d],x);
    124             if(n->ch[d]->r > n->r) rotate(n,d);
    125         }
    126         n->update();
    127     }
    128 }
    129 
    130 void rotate (node *&n,int d) // rotate n->ch[d] to n
    131 {
    132     node *k=n->ch[d];
    133     n->ch[d]=k->ch[d^1];
    134     k->ch[d^1]=n;
    135     n->update();
    136     k->update();
    137     n=k;
    138 }
    139 
    140 inline void mer (int x,int y)
    141 {
    142     if(roo[x]->s<roo[y]->s) swap(x,y);
    143     x=father(x);
    144     y=father(y);
    145     if(x==y) return;
    146     f[y]=x;
    147     int h=1,t=0;
    148     q[++t]=roo[y];
    149     node *k;
    150     while(h<=t)
    151     {
    152         k=q[h];
    153         ins(roo[x],k->v);
    154         if(k->ch[0]) q[++t]=k->ch[0];
    155         if(k->ch[1]) q[++t]=k->ch[1];
    156         h++;
    157     }
    158     roo[y]=roo[x];
    159 }
    160 
    161 int ask (node *&n,int k)
    162 {
    163     if(!n||k<0||n->s<k) return 0;
    164     int s=n->ch[0]?n->ch[0]->s:0;
    165     if(s<k&&k<=n->n+s) return n->v;
    166     if(s<k) return ask(n->ch[1],k-n->n-s);
    167     return ask(n->ch[0],k);
    168 }
    启发式合并-Treap
      
     1 # include <cstdio>
     2 # include <iostream>
     3 # include <cstring>
     4 # include <string>
     5 # include <algorithm>
     6 # include <cmath>
     7 # define R register int
     8 # define ll long long
     9 
    10 using namespace std;
    11 
    12 const int maxn=200005;
    13 int n,m,t[maxn<<5],ch[maxn<<5][2],v[maxn],roo[maxn],nod_cnt,l,r,k,true_value[maxn];
    14 struct node { int p,v; } a[maxn];
    15 
    16 bool cmp (node a,node b)
    17 {
    18     return a.v<b.v;
    19 }
    20 
    21 int build (int l,int r)
    22 {
    23     int id=++nod_cnt;
    24     if(l==r)
    25         return id;
    26     int mid=(l+r)>>1;
    27     ch[id][0]=build(l,mid);
    28     ch[id][1]=build(mid+1,r);
    29     return id;
    30 }
    31 
    32 int ins (int las,int l,int r,int pos,int v)
    33 {
    34     int id=++nod_cnt;
    35     if(l==r)
    36     {
    37         t[id]=t[las]+v;
    38         return id;
    39     }
    40     int mid=(l+r)>>1;
    41     ch[id][0]=ch[las][0];
    42     ch[id][1]=ch[las][1];
    43     if(pos<=mid) ch[id][0]=ins(ch[las][0],l,mid,pos,v);
    44     else ch[id][1]=ins(ch[las][1],mid+1,r,pos,v);
    45     t[id]=t[ ch[id][0] ]+t[ ch[id][1] ];
    46     return id;
    47 }
    48 
    49 int ask (int a,int b,int l,int r,int k)
    50 {
    51     if(l==r) return l;
    52     int mid=(l+r)>>1,x;
    53     x=t[ ch[b][0] ]-t[ ch[a][0] ];
    54     if(x>=k) return ask(ch[a][0],ch[b][0],l,mid,k);
    55     return ask(ch[a][1],ch[b][1],mid+1,r,k-x); 
    56 }
    57 
    58 int main()
    59 {
    60     scanf("%d%d",&n,&m);
    61     for (R i=1;i<=n;++i)
    62         scanf("%d",&a[i].v),a[i].p=i;
    63     sort(a+1,a+1+n,cmp);
    64     int cnt=0;
    65     a[0].v=a[1].v+1;
    66     for (R i=1;i<=n;++i)
    67     {
    68         if(a[i].v!=a[i-1].v) cnt++;
    69         v[ a[i].p ]=cnt;
    70         true_value[cnt]=a[i].v;
    71     }
    72     roo[0]=build(1,n);
    73     for (R i=1;i<=n;++i)
    74         roo[i]=ins(roo[i-1],1,n,v[i],1);
    75     for (R i=1;i<=m;++i)
    76     {
    77         scanf("%d%d%d",&l,&r,&k);
    78         if(l>r) swap(l,r);
    79         int x=ask(roo[l-1],roo[r],1,n,k);
    80         printf("%d
    ",true_value[x]);
    81     }
    82     return 0;
    83 }
    84 //又名根路径可持久化函数式权值线段树
    主席树
      
     1 # include <cstdio>
     2 # include <iostream>
     3 # include <cmath>
     4 # define R register int
     5 
     6 using namespace std;
     7 
     8 const int maxn=50004;
     9 int l,r,c,opt,n,siz;
    10 int a[maxn],b[maxn],delta[maxn];
    11 
    12 void add (int l,int r,int v)
    13 {
    14     if(b[l]==b[r])
    15     {
    16         for (R i=l;i<=r;++i)
    17             a[i]+=v;
    18     }
    19     else
    20     {
    21         if(b[l]*siz-l>l-(1+b[l]*siz-siz))
    22         {
    23             for (R i=1+b[l]*siz-siz;i<l;++i) a[i]-=v;
    24             delta[ b[l] ]+=v;
    25         }
    26         else
    27             for (R i=l;i<=b[l]*siz;++i) a[i]+=v;
    28         for (R i=b[l]+1;i<=b[r]-1;++i) delta[i]+=v;
    29         if(b[r]*siz-r>r-(1+b[r]*siz-siz))
    30             for (R i=1+b[r]*siz-siz;i<=r;++i) a[i]+=v;
    31         else
    32         {
    33             for (R i=r+1;i<=b[r]*siz;++i) a[i]-=v;
    34             delta[ b[r] ]+=v;
    35         }
    36     }
    37 }
    38 
    39 int main()
    40 {
    41     scanf("%d",&n);
    42     for (R i=1;i<=n;++i) scanf("%d",&a[i]);
    43     siz=sqrt(n);
    44     for (R i=1;i<=n;++i) b[i]=(i-1)/siz+1;
    45     for (R i=1;i<=n;++i)
    46     {
    47         scanf("%d%d%d%d",&opt,&l,&r,&c);
    48         if(opt==0)
    49             add(l,r,c);
    50         else
    51             printf("%d
    ",a[r]+delta[ b[r] ]);
    52     }
    53     return 0;
    54 }
    分块-区间加单点查询
      
      1 # include <cstdio>
      2 # include <iostream>
      3 # include <cmath>
      4 # include <algorithm>
      5 # define R register int
      6 # define ll long long
      7 # define P(i) sort(a+1+siz*(i-1),a+1+min(siz*i,n),cmp)
      8 
      9 using namespace std;
     10 
     11 const int maxn=100004;
     12 int id,n,siz,opt,l,r,c,ans;
     13 ll delta[maxn];
     14 struct dig
     15 {
     16     int b,k;
     17     ll v;
     18 }a[maxn];
     19 
     20 bool cmp (dig a,dig b) { return a.v<b.v; }
     21 
     22 void add (int l,int r,ll c)
     23 {
     24     if(a[l].b==a[r].b)
     25     {
     26         id=a[l].b;
     27         for (R i=1+siz*(id-1);i<=min(id*siz,n);++i)
     28             if(a[i].k>=l&&a[i].k<=r) a[i].v+=c;
     29         P(a[l].b);
     30     }
     31     else
     32     {
     33         id=a[l].b;
     34         for (R i=1+siz*(id-1);i<=min(siz*id,n);++i)
     35             if(a[i].k>=l&&a[i].k<=r)
     36                 a[i].v+=c;
     37         P(id);
     38         for (R i=a[l].b+1;i<=a[r].b-1;++i) delta[i]+=c;
     39         id=a[r].b;
     40         for (R i=1+siz*(id-1);i<=min(siz*id,n);++i)
     41             if(a[i].k>=l&&a[i].k<=r)
     42                 a[i].v+=c;
     43         P(id);
     44     }
     45 }
     46 
     47 int check (int x,ll c)
     48 {
     49     int l=1+siz*(x-1),r=min(n,siz*x),mid,ans=siz*(x-1);
     50     while (l<=r)
     51     {
     52         mid=r+((l-r)>>1);
     53         if(a[mid].v+delta[ a[mid].b ]<c)
     54             l=mid+1,ans=max(ans,mid);
     55         else
     56             r=mid-1;            
     57     }
     58     return ans-siz*(x-1);
     59 }
     60 
     61 int ask (int l,int r,ll c)
     62 {
     63     int ans=0,id;
     64     if(a[l].b==a[r].b)
     65     {
     66         id=a[l].b;
     67         for (R i=1+siz*(id-1);i<=min(siz*id,n);++i)
     68             if(a[i].k>=l&&a[i].k<=r&&a[i].v+delta[ a[i].b ]<c)
     69                 ans++;
     70     }
     71     else
     72     {
     73         id=a[l].b;
     74         for (R i=1+siz*(id-1);i<=min(siz*id,n);++i)
     75             if(a[i].k>=l&&a[i].k<=r&&a[i].v+delta[ a[i].b ]<c)
     76                 ans++;
     77         for (R i=a[l].b+1;i<=a[r].b-1;++i)
     78             ans+=check(i,c);    
     79         id=a[r].b;
     80         for (R i=1+siz*(id-1);i<=min(siz*id,n);++i)
     81             if(a[i].k>=l&&a[i].k<=r&&a[i].v+delta[ a[i].b ]<c)
     82                 ans++;
     83     }
     84     return ans;
     85 }
     86 
     87 int main()
     88 {
     89     scanf("%d",&n);
     90     siz=sqrt(n);
     91     for (R i=1;i<=n;++i)
     92     {
     93         scanf("%lld",&a[i].v);
     94         a[i].k=i;
     95         a[i].b=(i-1)/siz+1;
     96     }
     97     for (R i=1;i<=a[n].b;++i) P(i);
     98     for (R i=1;i<=n;++i)
     99     {
    100         scanf("%d%d%d%d",&opt,&l,&r,&c);
    101         if(opt)
    102         {            
    103             ans=ask(l,r,1LL*c*c);
    104             printf("%d
    ",ans);
    105         }
    106         else 
    107             add(l,r,c);
    108     }
    109     return 0;
    110 }
    分块-区间加区间排名
      
     1 # include <cstdio>
     2 # include <iostream>
     3 # include <cmath>
     4 # include <algorithm>
     5 # define R register int
     6 
     7 using namespace std;
     8 
     9 const int maxn=50004;
    10 int n,b[maxn],opt,l,r,c,siz;
    11 long long a[maxn],delta[maxn],s[maxn];
    12 
    13 void add (int l,int r,int c)
    14 {
    15     if(b[l]==b[r]) for (R i=l;i<=r;++i) a[i]+=c,s[ b[i] ]+=c;
    16     else
    17     {
    18         for (R i=l;i<=siz*b[l];++i) a[i]+=c,s[ b[i] ]+=c;
    19         for (R i=b[l]+1;i<=b[r]-1;++i) delta[i]+=c,s[i]+=siz*c;
    20         for (R i=1+siz*(b[r]-1);i<=r;++i) a[i]+=c,s[ b[i] ]+=c;
    21     }
    22 }
    23 
    24 int ask (int l,int r,int mod)
    25 {
    26     long long ans=0;
    27     if(b[l]==b[r]) for (R i=l;i<=r;++i) ans=(ans+a[i]+delta[ b[i] ])%mod;
    28     else
    29     {
    30         for (R i=l;i<=siz*b[l];++i) ans=(ans+a[i]+delta[ b[i] ])%mod;
    31         for (R i=b[l]+1;i<=b[r]-1;++i) ans=(ans+s[i])%mod;
    32         for (R i=1+siz*(b[r]-1);i<=r;++i) ans=(ans+a[i]+delta[ b[i] ])%mod;
    33     }
    34     return ans%mod;
    35 }
    36 
    37 int main()
    38 {
    39     scanf("%d",&n);
    40     siz=sqrt(n);
    41     for (R i=1;i<=n;++i) scanf("%lld",&a[i]);
    42     for (R i=1;i<=n;++i) b[i]=(i-1)/siz+1,s[ b[i] ]+=a[i];
    43     for (R i=1;i<=n;++i)
    44     {
    45         scanf("%d%d%d%d",&opt,&l,&r,&c);
    46         if(opt) printf("%d
    ",ask(l,r,c+1));
    47         else add(l,r,c);
    48     }
    49     return 0;
    50 }
    分块-区间加区间查询
      
     1 void init()
     2 {
     3     for (R i=1;i<=n;++i)
     4         st[i][0]=read();
     5     for (R k=1;k<=lg[n];++k)
     6         for (R i=1;i+(1<<k)-1<=n;++i)
     7             st[i][k]=max(st[i][k-1],st[i+(1<<(k-1))][k-1]);
     8 }
     9 
    10 int ask (int a,int b)
    11 {
    12     int k=lg[b-a+1];
    13     return max(st[a][k],st[b-(1<<k)+1][k]);
    14 }
    st表

    制胡窜

      好像$NOIP$从来没有考过真正的字符串算法啊,最多也就是读入输出,不过还是总结一下,反正会的也不多。那么就按照一本通的顺序好了。

      
     1 # include <cstdio>
     2 # include <iostream>
     3 # include <cstring>
     4 # include <string>
     5 # include <algorithm>
     6 # include <cmath>
     7 # define R register int
     8 # define ll long long
     9 # define ULL unsigned long long
    10 
    11 using namespace std;
    12 
    13 const int maxn=1000006;
    14 const int base=233;
    15 ULL po[maxn],Hash[maxn];
    16 char c[maxn];
    17 int n;
    18 
    19 ULL div_Hash (int l,int r) //获取子串的Hashֵ值
    20 {
    21     return Hash[r]-Hash[l]*po[r-l+1];
    22 }
    23 
    24 int main()
    25 {
    26     scanf("%s",c+1);
    27     n=strlen(c+1);
    28     po[0]=1;
    29     for (R i=1;i<=n;++i) po[i]=po[i-1]*base;
    30     for (R i=1;i<=n;++i) Hash[i]=Hash[i-1]*base+c[i];
    31     return 0;
    32 }
    Hash-自然溢出
      
     1 # include <cstdio>
     2 # include <iostream>
     3 # include <cstring>
     4 # include <string>
     5 # include <algorithm>
     6 # include <cmath>
     7 # define R register int
     8 # define ll long long
     9 # define ULL unsigned long long
    10 # define mod 1000000007
    11 
    12 using namespace std;
    13 
    14 const int maxn=1000006;
    15 const int base=233;
    16 ll po[maxn],Hash[maxn];
    17 char c[maxn];
    18 int n;
    19 
    20 ll div_Hash (int l,int r) //获取子串的Hashֵ值
    21 {
    22     return ((Hash[r]-Hash[l]*po[r-l+1])%mod+mod)%mod;
    23 }
    24 
    25 int main()
    26 {
    27     scanf("%s",c+1);
    28     n=strlen(c+1);
    29     po[0]=1;
    30     for (R i=1;i<=n;++i) po[i]=(po[i-1]*base)%mod;
    31     for (R i=1;i<=n;++i) Hash[i]=(Hash[i-1]*base+c[i])%mod;
    32     return 0;
    33 }
    Hash-模大质数
      
     1 # include <cstdio>
     2 # include <iostream>
     3 # include <cstring>
     4 # include <string>
     5 # include <algorithm>
     6 # include <cmath>
     7 # define R register int
     8 # define ll long long
     9 
    10 using namespace std;
    11 
    12 const int mod=19260817;
    13 const int maxn=1000005;
    14 int h,n,p1=1,ans,p2=1,a[maxn],v[maxn],firs[mod+10],nex[mod+10];
    15 
    16 bool que (int x)
    17 {
    18     int hash=x;
    19     while (hash>mod) hash-=mod;
    20     for (R i=firs[hash];i;i=nex[i])
    21         if(v[i]==x) return true;
    22     return false;
    23 }
    24 
    25 void add (int x)
    26 {
    27     int hash=x;
    28     while (hash>mod) hash-=mod;
    29     v[++h]=x;
    30     nex[h]=firs[hash];
    31     firs[hash]=h;
    32 }
    33 
    34 void del (int x)
    35 {
    36     int hash=x;
    37     while (hash>mod) hash-=mod;
    38     for (R i=firs[hash];i;i=nex[i])
    39         if(v[i]==x)
    40         {
    41             v[i]=-1;
    42             return ;
    43         }
    44 }
    45 
    46 int main()
    47 {
    48 
    49     return 0;
    50 }
    哈希表
      
     1 # include <cstdio>
     2 # include <iostream>
     3 # include <cstring>
     4 # include <string>
     5 # include <algorithm>
     6 # include <cmath>
     7 # define R register int
     8 # define ll long long
     9 
    10 using namespace std;
    11 
    12 const int maxn=1000006;
    13 char s[maxn],t[maxn];
    14 int p[maxn],ls,lt,j;
    15 
    16 int main()
    17 {
    18     scanf("%s",s+1);
    19     scanf("%s",t+1);
    20     ls=strlen(s+1);
    21     lt=strlen(t+1);
    22     p[1]=0;
    23     for (R i=2;i<=lt;++i)
    24     {
    25         j=p[i-1];
    26         while(j&&t[i]!=t[j+1]) j=p[j];
    27         if(t[i]==t[j+1]) p[i]=j+1;
    28         else p[i]=0;
    29     }
    30     j=0;
    31     for (R i=0;i<ls;++i)
    32     {
    33         while(j&&a[i+1]!=b[j+1]) j=p[j];
    34         if(a[i+1]==b[i+1]) j++;
    35         if(j==lt) ans++;
    36     }
    37     return 0;
    38 }
    kmp
      
     1 # include <cstdio>
     2 # include <iostream>
     3 # include <cstring>
     4 # include <string>
     5 # include <algorithm>
     6 # include <cmath>
     7 # define R register int
     8 # define ll long long
     9 
    10 using namespace std;
    11 
    12 const int maxn=100005*32;
    13 int n,cnt,h,a[40];
    14 struct Trie_01
    15 {
    16     int ch[maxn][2];
    17     int vis[maxn];
    18     void clear()
    19     {
    20         memset(ch,0,sizeof(ch));
    21         memset(vis,0,sizeof(vis));
    22     }
    23     void insert()
    24     {
    25         int x=1;
    26         for (R i=1;i<=32;++i)
    27         {
    28             if(!ch[x][ a[i] ])
    29                 ch[ x ][ a[i] ]=++cnt;
    30             x=ch[x][ a[i] ];
    31         }
    32         vis[x]++;
    33     }
    34     int find()
    35     {
    36         int ans=0,x=1;
    37         for (R i=1;i<=32;++i)
    38         {
    39             if(ch[x][ a[i]^1 ])
    40             {
    41                 ans=ans<<1|1;
    42                 x=ch[x][ a[i]^1 ];
    43             }
    44             else x=ch[x][ a[i] ];
    45         }
    46         return ans;
    47     }
    48 }t;
    49 
    50 void spilt (int x)
    51 {
    52     h=0;
    53     while(x) a[++h]=x,x/=2;
    54     for (R i=1;i<=h/2;++i) swap(a[i],a[h-i+1]);
    55 }
    56 
    57 int main()
    58 {
    59 
    60     return 0;
    61 }
    0-1Trie
      
     1 # include <cstdio>
     2 # include <iostream>
     3 # include <cstring>
     4 # include <string>
     5 # include <algorithm>
     6 # include <cmath>
     7 # define R register int
     8 # define ll long long
     9 
    10 using namespace std;
    11 
    12 const int maxn=100005;
    13 int n,cnt,len;
    14 char c[maxn];
    15 struct Trie_char
    16 {
    17     int ch[maxn][27];
    18     int vis[maxn];
    19     void clear()
    20     {
    21         memset(ch,0,sizeof(ch));
    22         memset(vis,0,sizeof(vis));
    23     }
    24     void insert()
    25     {
    26         int x=1,n;
    27         for (R i=1;i<=len;++i)
    28         {
    29             n=c[i]-'a';
    30             if(!ch[x][ no ])
    31                 ch[ x ][ no ]=++cnt;
    32             x=ch[x][ no ];
    33         }
    34         vis[x]++;
    35     }
    36     bool find()
    37     {
    38         int no,x=1;
    39         for (R i=1;i<=len;++i)
    40         {
    41             no=a[i]-'a';
    42             if(!ch[x][no]) return false;
    43             x=ch[x][no];
    44         }
    45         return vis[x];
    46     }
    47 }t;
    48 
    49 int main()
    50 {
    51     scanf("%s",c+1);
    52     len=strlen(c+1);
    53     return 0;
    54 }
    char-Trie

    其它:

      
     1 # include <cstdio>
     2 # include <iostream>
     3 # include <cstring>
     4 # include <string>
     5 # include <algorithm>
     6 # include <cmath>
     7 # define R register int
     8 # define ll long long
     9 
    10 using namespace std;
    11 
    12 const int maxn=41;
    13 int n,l,r;
    14 ll m,a[maxn],ans,x;
    15 ll lef[1<<21],rig[1<<21];
    16 
    17 void dfs (int x,int l,int r,int col,ll S)
    18 {
    19     if(x==r+1)
    20     {
    21         if(col==1) lef[ ++lef[0] ]=S;
    22         else rig[ ++rig[0] ]=S;
    23         return ;
    24     }
    25     dfs(x+1,l,r,col,S+a[x]);
    26     dfs(x+1,l,r,col,S);
    27 }
    28 
    29 int main()
    30 {
    31     scanf("%d%lld",&n,&m);
    32     for (R i=1;i<=n;++i)
    33         scanf("%lld",&a[i]);
    34     int mid=n/2;
    35     dfs(1,1,mid,1,0);
    36     dfs(mid+1,mid+1,n,2,0);
    37     sort(lef+1,lef+lef[0]+1);
    38     sort(rig+1,rig+rig[0]+1);
    39     l=-1;
    40     r=rig[0];
    41     for (R i=1;i<=lef[0];++i)
    42     {
    43         x=lef[i];
    44         while(r&&x+rig[r]>m) r--;
    45         if(l==-1) l=r;
    46         while(l&&x+rig[l]<=m) l--;
    47         ans+=(r-l);
    48     }
    49     printf("%lld",ans);
    50     return 0;
    51 }
    meet in the middle
      
     1 int find_lef (int x) //x的前驱
     2 {
     3     int l=1,r=n,mid,ans=0;
     4     while(l<=r)
     5     {
     6         mid=(l+r)>>1;
     7         if(a[mid]<x)
     8             ans=max(ans,mid),l=mid+1;
     9         else
    10             r=mid-1;
    11     }
    12     return ans;
    13 }
    14 
    15 int find_rig (int x) //x的后继
    16 {
    17     int l=1,r=n,mid,ans=n;
    18     while(l<=r)
    19     {
    20         mid=(l+r)>>1;
    21         if(a[mid]>x)
    22             ans=min(ans,mid),r=mid-1;
    23         else
    24             l=mid+1;
    25     }
    26     return ans;
    27 }
    二分法
      
     1 double open_up () //开口朝上的函数
     2 {
     3     double l=-inf,r=inf,lmid,rmid;
     4     while(r-l>=eps)
     5     {
     6         lmid=l+(l+r)/3.0;
     7         rmid=r-(l+r)/3.0;
     8         if(f(lmid)>f(rmid))
     9             l=lmid;
    10         else
    11             r=rmid;
    12     }
    13     return f(l);
    14 }
    15 
    16 double open_down()//开口朝下的函数
    17 {
    18     double l=-inf,r=inf,lmid,rmid;
    19     while(r-l>=eps)
    20     {
    21         lmid=l+(l+r)/3.0;
    22         rmid=r-(l+r)/3.0;
    23         if(f(lmid)<f(rmid))
    24             l=lmid;
    25         else
    26             r=rmid;
    27     }
    28     return f(l);
    29 }
    三分

    建议:

      1.每道题做完后可以开着$O_2$测一下,可能能查出来一些内存方面或者是局部变量忘记清零这样的错误.

      2.多组数据的题一定要记得清空数组,可以把所有定义的数组都先清空再看哪些是不必要的,定义了$STL$的队列一定要用$q.pop()$清空,千万不要用$q.front()$.所有的变量也都要清为初始状态,注意初始状态不一定是$0$!

      这里还有$asuldb$的模板库:https://35178.blog.luogu.org/noip-qian-di-ban-zi-men

      最大值赋得不够大:$memset$一个 $int$ 数组全为 $1$ 还是比 $10^9$ 小的,可以记录$-1$作为初始状态或是直接用$ll$.

      离线处理询问后忘了调回原来的顺序:记录$id$,处理完后重排序;

      奇妙的$CE$:用命令行编译可以彻底杜绝此类问题,注意编译之前另存一份,防止被编译没了.

      不要用英语单词做变量名,不要用除了$n,m,k,x,y,a,b,c,t$之外的单个字母做变量名.

      树链剖分时不要用top做变量名.

  • 相关阅读:
    3.2spring源码系列----循环依赖源码分析
    3.1 spring5源码系列--循环依赖 之 手写代码模拟spring循环依赖
    Jetson AGX Xavier ROS 调用usb单目摄像头运行ORB_SLAM2
    Jetson AGX Xavier ROS下调用USB单目摄像头
    SpringCloud-OpenFeign组件的使用
    SpringCloud-服务间通信方式
    SpringCloud-服务注册中心
    SpringCloud入门
    K8s—集群搭建
    Redis—过期策略以及内存淘汰机制
  • 原文地址:https://www.cnblogs.com/shzr/p/9890352.html
Copyright © 2011-2022 走看看