给个人认为比较难的题目打上'*'

NOIP2002(clear)

 //一个很吼的贪心题,将平均数减掉之后从左往右将影响消除
 #include<bits/stdc++.h>
 using namespace std;
 ];
 int main()
 {
      , sum = ;
     cin >> n;
      ; i < n ; i++)
     {
         cin >> num[i];
         sum += num[i];
     }
     sum /= n;
      ; i < n ; i++)
     {
         num[i] -= sum;
         if(num[i])
         {
             cou++;
             num[i + ] += num[i];
         }
     }
     cout << cou;
     ;
 }

均分纸牌

 //bfs,注意一个串可能可以变换成多个串
 #include<bits/stdc++.h>
 using namespace std;
 struct p{
     string n;
     int s;
 }ans;
 set < string > uni;
 multimap < string , string > dis;
 queue < p > q;
 int main()
 {
     string tar , a , b;
     cin >> ans.n >> tar;
     q.push(ans);
     uni.insert(ans.n);
     while(cin >> a >> b)    dis.insert(pair<string , string>(a , b));
     while(!q.empty())
     {
         ans = q.front();
         q.pop();
         )    break;
         if(ans.n == tar)
         {
             cout << ans.s;
             ;
         }
         ans.s++;
          ; i < ans.n.size() ; i++)
              ; j <= i ; j++)
                 )))
                     for(multimap<string , string>::iterator iter = dis.begin() ; iter != dis.end() ; iter++)
                         ))
                         {
                              , j) + iter -> second +  , (int)ans.n.length() - i);
                             if(!uni.count(newS))
                             {
                                 uni.insert(newS);
                                 p t;
                                 t.n = newS;
                                 t.s = ans.s;
                                 q.push(t);
                             }
                         }
     }
     cout << "NO ANSWER!";
     ;
 }

字串变换

 //题目叙述似乎不是很清楚,看懂了直接上公式就行
 #include<bits/stdc++.h>
 #define eps 1e-4
 //This code is written by Itst
 using namespace std;

 int main(){
 #ifdef LG
     freopen("1033.in" , "r" , stdin);
     //freopen("1033.out" , "w" , stdout);
 #endif
     long double H , S , V , L , K , N;
     cin >> H >> S >> V >> L >> K >> N;
     long double rangeR = eps + S + L - V * sqrt((H - K) * 0.2) , rangeL = S - eps - V * sqrt(H * 0.2);
     ;
      ; i < N ; i++)
         if(i >= rangeL && i <= rangeR)
             cnt++;
     cout << cnt;
     ;
 }

自由落体

 //爆搜+覆盖剪枝+最优化剪枝
 #include<bits/stdc++.h>
 //This code is written by Itst
 using namespace std;

 inline int read(){
     ;
     ;
     char c = getchar();
     while(c != EOF && !isdigit(c)){
         if(c == '-')
             f = ;
         c = getchar();
     }
     while(c != EOF && isdigit(c)){
         a = (a << ) + (a << ) + (c ^ ');
         c = getchar();
     }
     return f ? -a : a;
 }

 ][] , tria[][] , N , K , ans = 0x7fffffff;

 bool check(int i , int j){
     ] < tria[j][] || tria[j][] < tria[i][] || tria[i][] < tria[j][] || tria[i][] > tria[j][];
 }

 void dfs(int now , int sum){
     if(sum > ans)
         return;
     if(now > N){
         ans = sum;
         return;
     }
     ][] , newSum = sum;
     memcpy(temp , tria , sizeof(tria));
      ; i <= K ; i++){
         ] < tria[i][])
             newSum -= (tria[i][] - tria[i][]) * (tria[i][] - tria[i][]);
         tria[i][] = min(tria[i][] , node[now][]);
         tria[i][] = max(tria[i][] , node[now][]);
         tria[i][] = min(tria[i][] , node[now][]);
         tria[i][] = max(tria[i][] , node[now][]);
         newSum += (tria[i][] - tria[i][]) * (tria[i][] - tria[i][]);
         ;
          ; f && j <= K ; j++)
             if(j != i)
                 f = check(i , j);
         if(f)
             dfs(now +  , newSum);
         memcpy(tria , temp , sizeof(tria));
         newSum = sum;
     }
 }

 int main(){
 #ifdef OJ
     freopen("1034.in" , "r" , stdin);
     //freopen("1034.out" , "w" , stdout);
 #endif
     N = read();
     K = read();
      ; i <= N ; i++){
         node[i][] = read();
         node[i][] = read();
     }
      ; i <= K ; i++){
         tria[i][] = tria[i][] = ;
         tria[i][] = tria[i][] = ;
     }
     dfs( , );
     cout << ans;
     ;
 }

*矩形覆盖

NOIP2003(clear)

 //拓扑排序模板题
 #include<bits/stdc++.h>
 using namespace std;
 inline int read(){
     ;
     ;
     char c = getchar();
     while(!isdigit(c)){
         ;
         c = getchar();
     }
     ) + (a << ) + (c ^ ') , c = getchar();
     return k ? -a : a;
 }
 vector < ] , W[];
 ] , U[] , num[];
 int main(){
     int N = read() , P = read();
     queue < int > q;
     priority_queue < int , vector < int > , greater < int > > q1;
      ; i <= N ; i++){
         if(C[i] = read()){
             q.push(i);
             read();
         }
         else    C[i] -= read();
     }
     while(P--){
         int a = read() , b = read();
         Ed[a].push_back(b);
         W[a].push_back(read());
         num[b]++;
     }
     while(!q.empty()){
         int t = q.front();
         q.pop();
         if(Ed[t].size())
              ; i ^ Ed[t].size() ; i++){
                 )    C[Ed[t][i]] += W[t][i] * C[t];
                 if(!--num[Ed[t][i]])    q.push(Ed[t][i]);
             }
         )    q1.push(t);
     }
     if(q1.empty())    cout << "NULL";
     while(!q1.empty()){
         cout << q1.top() << ' ' << C[q1.top()] << endl;
         q1.pop();
     }
     ;
 }

神经网络

 //区间DP,设f[i][j]表示i到j的点组成的二叉树中得分最高的方式,合并枚举根即可
 #include<bits/stdc++.h>
 using namespace std;
 ] , p[][];
 ][];
 void dfs(int f , int l)
 {
     if(f >= l)
     {
         if(f == l)    cout << f << " ";
         return;
     }
     cout << p[f][l] << " ";
     dfs(f , p[f][l] - );
     dfs(p[f][l] +  , l);
 }
 int main(){
     ios::sync_with_stdio(false);
     cin >> n;
      ; i <= n ; i++)    vis[][i] = ;
      ; i <= n ; i++)
     {
          ; j <= n ; j++)    vis[i][j] = ;
         cin >> num[i];
         vis[i][i] = num[i];
     }
      ; i <= n ; i++)    vis[n + ][i] = ;
      ; i <= n -  ; i++)
          ; j + i <= n ; j++)
             for(int k = j ; k <= j + i ; k++)
                 ] * vis[k + ][j + i] + num[k] > vis[j][i + j])
                 {
                     vis[j][i + j] = vis[j][k - ] * vis[k + ][j + i] + num[k];
                     p[j][j + i] = k;
                 }
     cout << vis[][n] << endl;
     dfs( , n);
     ;
 }

加分二叉树

 //暴搜,根据贪心不难知道每一次切断的一定是当前被感染的点和其没被感染的儿子之间的边
 #include<bits/stdc++.h>
 using namespace std;
 inline int read(){
     ;
     char c = getchar();
     while(!isdigit(c))    c = getchar();
     ) + (a << ) + (c ^ ) , c = getchar();
     return a;
 }
 inline int min(int a , int b){
     return a < b ? a : b;
 }
 vector < ];
 queue < int > q;
 int minN = 0x3f3f3f3f;
 ];
 void choose(int , queue < int >);
 void create(int num , queue < int > q){
     queue < int > q1;
     register ;
     while(!q.empty()){
         int t = q.front();
         q.pop();
         num++;
          ; i < Ed[t].size() ; i++)
             if(!vis[Ed[t][i]]){
                 q1.push(Ed[t][i]);
                 if(num + ++sum > minN)    return;
             }
     }
     if(num + sum > minN)    return;
     ){
         minN = min(minN , num);
         return;
     }
     choose(num , q1);
 }
 int main(){
     register int n = read() , p = read();
      ; i - p ; i++){
         int a = read() , b = read();
         Ed[a].push_back(b);
         Ed[b].push_back(a);
     }
     q.push();
     vis[] = ;
     create( , q);
     printf("%d" , minN);
     ;
 }
 void choose(int num , queue < int > q){
     register int first = q.front();
     do{
         vis[q.front()] = ;
         q.push(q.front());
         q.pop();
     }while(q.front() - first);
     do{
         register int t = q.front();
         q.pop();
         create(num , q);
         q.push(t);
     }while(q.front() - first);
     while(!q.empty()){
         vis[q.front()] = ;
         q.pop();
     }
 }

传染病控制

 //为什么会有这么玄学的题目???
 //注意:①I可能为人名;②在某种状态没有人被认为时Guilty的时候,考虑被指正不是Guilty的人;③有可能多种情况同一结果
 #include<bits/stdc++.h>
 //This code is written by Itst
 using namespace std;

 inline int read(){
     ;
     ;
     char c = getchar();
     while(c != EOF && !isdigit(c)){
         if(c == '-')
             f = ;
         c = getchar();
     }
     while(c != EOF && isdigit(c)){
         a = (a << ) + (a << ) + (c ^ ');
         c = getchar();
     }
     return f ? -a : a;
 }

 map < string , int > day , name;
 ][] , notG[][] , date[][] , mark[] , nowG[] , nowNotG[] , nowDate[] , nowNotDate[];
 int N , M , P;
 ];

 void check(){
     memset(nowG ,  , sizeof(nowG));
     memset(nowNotG ,  , sizeof(nowNotG));
     memset(nowDate ,  , sizeof(nowDate));
     memset(nowNotDate ,  , sizeof(nowNotDate));
      ; i <= M ; i++)
         if(!mark[i]){
              ; j <= M ; j++)
                 if(G[i][j])
                     nowG[j] = ;
              ; j <= M ; j++)
                 if(notG[i][j])
                     nowNotG[j] = ;
              ; j <=  ; j++)
                 if(date[i][j])
                     nowDate[j] = ;
         }
         else{
              ; j <= M ; j++)
                 if(G[i][j])
                     nowNotG[j] = ;
              ; j <= M ; j++)
                 if(notG[i][j])
                     nowG[j] = ;
              ; j <=  ; j++)
                 if(date[i][j])
                     nowNotDate[j] = ;
         }
      , ifGuilty = ;
      ; i <= M ; i++)
         if(nowG[i])
             if(ifGuilty || nowNotG[i])
                 return;
             else
                 ifGuilty = ;
      ; i <=  ; i++)
         if(nowDate[i])
             if(ifDate || nowNotDate[i])
                 return;
             else
                 ifDate = ;
     if(!ifGuilty)
          ; i <= M ; i++)
             if(!nowNotG[i])
                 if(!ifGuilty)
                     ifGuilty = ;
                 else{
                     puts("Cannot Determine");
                     exit();
                 }
     if(ifGuilty){
          ; i <= M ; i++)
             if(nowG[i]){
                 if(!answer.empty() && answer != ori[i]){
                     puts("Cannot Determine");
                     exit();
                 }
                 answer = ori[i];
                 return;
             }
          ; i <= M ; i++)
             if(!nowNotG[i]){
                 if(!answer.empty() && answer != ori[i]){
                     puts("Cannot Determine");
                     exit();
                 }
                 answer = ori[i];
                 return;
             }
     }
     else{
         puts("Cannot Determine");
         exit();
     }
 }

 void dfs(int now , int cnt){
     if(now > M){
         if(cnt == N)
             check();
         return;
     }
     dfs(now +  , cnt);
     mark[now] = ;
     dfs(now +  , cnt + );
     mark[now] = ;
 }

 int main(){
 #ifdef OJ
     freopen("1039.in" , "r" , stdin);
     //freopen("1039.out" , "w" , stdout);
 #endif
     day[;
     day[;
     day[;
     day[;
     day[;
     day[;
     day[;
     M = read();
     N = read();
     P = read();
     string s , now;
      ; i <= M ; i++){
         cin >> ori[i];
         name[ori[i]] = i;
     }
     getline(cin , s);
     stringstream ss;
      ; i <= P ; i++){
         getline(cin , s);
         if(!s.empty() && *--s.end() == '\r')
             s.erase(--s.end());
         ss.clear();
         ss.str(s);
         ss >> s;
         s.erase(--s.end());
         int t = name[s];
         if(!t)
             continue;
         while(ss >> s)
             if(s == "I"){
                 ss >> now;
                 if(now != "am"){
                     if(now != "is" || !name.count("I"))
                         break;
                     int k = name["I"];
                     ss >> now;
                     if(now != "guilty." && now != "not")
                         break;
                     if(now == "guilty.")
                         G[t][k] = ;
                     else{
                         ss >> now;
                         if(now == "guilty.")
                             notG[t][k] = ;
                     }
                     continue;
                 }
                 ss >> now;
                 if(now != "guilty." && now != "not")
                     break;
                 if(now == "guilty.")
                     G[t][t] = ;
                 else{
                     ss >> now;
                     if(now == "guilty.")
                         notG[t][t] = ;
                 }
             }
             else
                 if(name.count(s)){
                     int k = name[s];
                     ss >> now;
                     if(now != "is")
                         break;
                     ss >> now;
                     if(now != "guilty." && now != "not")
                         break;
                     if(now == "guilty.")
                         G[t][k] = ;
                     else{
                         ss >> now;
                         if(now == "guilty.")
                             notG[t][k] = ;
                     }
                 }
                 else
                     if(s == "Today"){
                         ss >> now;
                         if(now != "is")
                             break;
                         ss >> now;
                         if(now.empty())
                             break;
                         now.erase(--now.end());
                         if(!day.count(now))
                             break;
                         date[t][day[now]] = ;
                     }
                     else
                         break;
     }
     dfs( , );
     if(answer.empty())
         puts("Impossible");
     else
         cout << answer;
     ;
 }

*侦探推理

NOIP2004(clear)

 //...
 #include<bits/stdc++.h>
 using namespace std;
 int main()
 {
      , c = ;
      ; i <=  ; i++)
     {
         int a;
         cin >> a;
         if(mon < a)
         {
             cout << "-" << i;
             ;
         }
         c += (mon - a) /  * ;
         mon = (mon - a) %  + ;
     }
     cout << c /  *  + mon - ;
     ;
 }

津津的储蓄计划

 //每一次贪心地合并两个重量最少的果子
 #include<bits/stdc++.h>
 using namespace std;
 queue <int> p , q;
 ];
 int main(){
     ;
     cin >> n;
      ; i < n ; i++)    cin >> a[i];
     sort(a , a + n);
      ; i < n ; i++)    p.push(a[i]);
      ; !p.empty() || q.size() !=  ; i++)
     {
         int a , b;
         if(p.empty())
         {
             a = q.front();
             q.pop();
         }
         else
             if(q.empty())
             {
                 a = p.front();
                 p.pop();
             }
             else
             {
                 int x = p.front() , y = q.front();
                 if(x <= y)
                 {
                     a = x;
                     p.pop();
                 }
                 else
                 {
                     a = y;
                     q.pop();
                 }
             }
         if(p.empty())
         {
             b = q.front();
             q.pop();
         }
         else
             if(q.empty())
             {
                 b = p.front();
                 p.pop();
             }
             else
             {
                 int x = p.front() , y = q.front();
                 if(x <= y)
                 {
                     b = x;
                     p.pop();
                 }
                 else
                 {
                     b = y;
                     q.pop();
                 }
             }
         sum += a + b;
         q.push(a + b);
     }
     cout << sum;
     ;
 }

合并果子

 //DP,从左往右、从右往左做两边LIS算最大权值
 #include<bits/stdc++.h>
 using namespace std;
 ] , b[] , c[];
 int main()
 {
     std::ios::sync_with_stdio(false);
     ;
     cin >> n;
      ; i < n ; i++)
     {
         cin >> num[i];
          ; j +  ; j--)
             if(num[i] > num[j] && b[i] < b[j])
                 b[i] = b[j];
         b[i]++;
     }
      ; i +  ; i--)
     {
          ; j - n ; j++)
             if(num[i] > num[j] && c[i] < c[j])
                 c[i] = c[j];
         c[i]++;
         maxN = max(maxN , b[i] + c[i] - );
     }
     cout << n - maxN;
     ;
 }

合唱队形

 //搜索要注意剪枝(看前边是否有不论进位与否都不满足条件的竖式),也可以高斯消元
 #include<bits/stdc++.h>
 using namespace std;
 ][];
 ] , N , num[] , vis[];
 void dfs(int a , int i)
 {
     )
      {
           ; i < N ; i++)
             printf("%d " , num[i]);
         exit();
      }
       ; k < a ; k++)
         ][k] -  && num[s[][k] -  && num[s[][k] -  && (num[s[][k] - ][k] - ][k] - ][k] - ][k] -  - num[s[][k] - 'A']) % N)
             return;
     ][a] -  && num[s[][a] -  && num[s[][a] - )
     {
         ][a] - ][a] - ][a] - 'A'])
         {
             jw[a - ] = (num[s[][a] - ][a] - 'A'] + jw[a]) / N;
             ]);
                 dfs(a -  , );
         }
     }
     else
         )
         {
                 ][a] - ][a] - 'A'] + jw[a];
                ][a] - 'A'] != n % N)
                    return;
                jw[a - ] = n / N;
                ][a] - )
                {
                    num[s[][a] - 'A'] = n % N;
                    vis[n % N] = ;
                    dfs(a -  , );
                    vis[n % N] = ;
                    num[s[][a] - ;
                }
                else
                    dfs(a -  , );
            }
            else
                ))
                {
                    ; j >=  ; j--)
                        if(!vis[j])
                        {
                            vis[j] = ;
                            num[s[i][a] - 'A'] = j;
                            dfs(a , i + );
                            num[s[i][a] - ;
                            vis[j] = ;
                        }
                }
                else
                    dfs(a , i + );
 }
 int main()
 {
     scanf(] , s[] , s[]);
     memset(num , - , sizeof(num));
     dfs(N -  , );
     ;
 }

*虫食算

NOIP2005(clear)

 //条件判断练习题
 #include<bits/stdc++.h>
 #define I ans[i].
 using namespace std;
 struct scho{
     string name;
     char gb , xb;
     int numL , aveSco , claSco , scho;
     inline void input()
     {
         cin >> name >> aveSco >> claSco >> gb >> xb >> numL;
          && numL)    scho += ;
          && claSco > )    scho += ;
         )    scho += ;
         )    scho += ;
         )    scho += ;
     }
 }ans[];
 int main()
 {
     ios::sync_with_stdio(false);
      , maxScho = - , maxD = ;
     cin >> n;
      ; i < n ; i++)
     {
         ans[i].input();
         sumScho += ans[i].scho;
         if(maxScho < ans[i].scho)
         {
             maxScho = ans[i].scho;
             maxD = i;
         }
     }
     cout << ans[maxD].name << endl << maxScho << endl << sumScho;
     ;
 }

谁拿了最多奖学金

 //DP并压缩路径,根据NOIP2017D1T1结论可以知道当路径长度>=72的时候可以直接压成72,因为72以及之后的都一定可以被到达
 //然而代码里面压的是2520
 #include<bits/stdc++.h>
 using namespace std;
 ] , c[] , minN[];
 ];
 inline int min(int a , int b){
     return a < b ? a : b;
 }
 int main(){
     int L , S , T , M;
     scanf("%d%d%d%d" , &L , &S , &T , &M);
      ; i < M ; i++)    scanf("%d" , a + i);
     sort(a , a + M);
     a[M] = L;
     c[] = a[] % ;
      ; i <= M ; i++){
         ] , b = tmp % ;
          && b <= T)    b += ;
         c[i] = c[i - ] + b;
     }
      ; i < M ; i++)    f[c[i]] = ;
     memset(minN , 0x3f , sizeof(minN));
     minN[] = ;
      ; i < c[M] ; i++){
         for(int j = S; j <= T && j <= i ; j++)
             minN[i] = min(minN[i] , minN[i - j]);
         minN[i] += f[i];
     }
     int Min = 0x3f3f3f3f;
     for(int i = c[M] - T ; i - c[M] ; i++)
         Min = min(Min , minN[i]);
     cout << Min;
     ;
 }

*过河

 //正着、反着把环断成链,考虑最多有多少个人可以不移动
 #include<bits/stdc++.h>
 //This code is written by Itst
 using namespace std;

 inline int read(){
     ;
     ;
     char c = getchar();
     while(c != EOF && !isdigit(c)){
         if(c == '-')
             f = ;
         c = getchar();
     }
     while(c != EOF && isdigit(c)){
         a = (a << ) + (a << ) + (c ^ ');
         c = getchar();
     }
     return f ? -a : a;
 }

 ;
 ];
 bool vis[MAXN];

 int main(){
 #ifdef OJ
     freopen("1053.in" , "r" , stdin);
     //freopen("1053.out" , "w" , stdout);
 #endif
      , cnt = ;
      ; i <= N ; i++){
         l[i] = read();
         r[i] = read();
     }
     pre = l[];
     vis[] = ;
     pot[] = ;
      ; i <= N ; i++){
         if(l[dir] == pre){
             pre = dir;
             dir = r[dir];
         }
         else{
             pre = dir;
             dir = l[dir];
         }
         if(vis[dir]){
             puts("-1");
             ;
         }
         vis[dir] = ;
         pot[(i - dir + N) % N]++;
     }
      ; i < N ; i++)
         cnt = max(cnt , pot[i]);
     memset(pot ,  , sizeof(pot));
     pre = r[];
     dir = ;
     pot[] = ;
      ; i <= N ; i++){
         if(l[dir] == pre){
             pre = dir;
             dir = r[dir];
         }
         else{
             pre = dir;
             dir = l[dir];
         }
         pot[(i - dir + N) % N]++;
     }
      ; i < N ; i++)
         cnt = max(cnt , pot[i]);
     printf("%d\n" , N - cnt);
     ;
 }

篝火晚会

 //找到值带入a即可
 #include<bits/stdc++.h>
 #define int long long
 //This code is written by Itst
 using namespace std;

 inline int read(){
     ;
     ;
     char c = getchar();
     while(c != EOF && !isdigit(c)){
         if(c == '-')
             f = ;
         c = getchar();
     }
     while(c != EOF && isdigit(c)){
         a = (a << ) + (a << ) + (c ^ ');
         c = getchar();
     }
     return f ? -a : a;
 }

 ;
 ][] = { ,  ,  ,  ,  ,  ,  ,  ,  ,  ,  , };
 ] = "()^*+-";
 ];
 ];
 ] , pos[];
 map < char , int > ctoi;

 int calc(int a , int b , int pos){
     ;
     switch(pos){
     :
         while(b){
             )
                 ans = ans * a % MOD;
             a = a * a % MOD;
             b >>= ;
         }
         break;
     :
         ans = a * b % MOD;
         break;
     :
         ans = (a + b) % MOD;
         break;
     :
         ans = (a - b + MOD) % MOD;
         break;
     }
     return ans;
 }

 int calc(string s , int a){
      , topPos =  , nowNum = ;
     ;
     pos[] = ;
     s = s + ")";
      ; i < s.size() ; i++)
         if(s[i] == ' ' || s[i] == '\r' || s[i] == '\n')
             continue;
         else
             if(isdigit(s[i])){
                 nowNum = nowNum *  + s[i] - ';
                 f = ;
             }
             else
                 if(s[i] == 'a')
                     num[++topNum] = a;
                 else{
                     if(f){
                         num[++topNum] = nowNum;
                         nowNum = f = ;
                     }
                     int t = ctoi[s[i]];
                     ] > yxj[t][]){
                         num[topNum - ] = calc(num[topNum - ] , num[topNum] , pos[topPos]);
                         topNum--;
                         topPos--;
                     }
                     ] == yxj[t][])
                         topPos--;
                     else
                         pos[++topPos] = t;
                 }
     ];
 }

 inline void getString(string& s){
     char c = getchar();
     while(c == '\r' || c == '\n')
         c = getchar();
     while(!(c == '\r' || c == '\n' || c == EOF)){
         s = s + c;
         c = getchar();
     }
 }

 signed main(){
 #ifdef OJ
     freopen("1054.in" , "r" , stdin);
     //freopen("1054.out" , "w" , stdout);
 #endif
      ; i <  ; i++)
         ctoi[to[i]] = i;
     getString(mod);
     int N = read();
      ; i <= N ; i++)
         getString(now[i]);
      ; i <=  ; i++){
         int t = calc(mod , i);
          ; j <= N ; j++)
             if(calc(now[j] , i) != t)
                 vis[j] = ;
     }
      ; i <= N ; i++)
         if(!vis[i])
             putchar(i + );
     ;
 }

等价表达式

NOIP2006(clear)

 //区间DP、断环成链
 #include<bits/stdc++.h>
 #define ll long long
 using namespace std;
 inline ll fast_read()
 {
     char c = getchar();
     ll a = ;
     ;
     while(!isdigit(c))
     {
         ;
         c = getchar();
     }
     ) + (a << ) + c - ' , c = getchar();
     return k ? -a : a;
 }
 inline void fast_print(ll x)
 {
     ] , dirN = -;
     )    putchar('-') , x = -x;
      , x /= ;
     )    putchar(');
     )    putchar(num[dirN--] + );
     putchar('\n');
 }
 ] , maxN[][];
 int main()
 {
     ;
      ; i < m ; i++)    num[i] = fast_read();
      ; i <= m ; i++)
          ; j < m ; j++)
              ; k < i + j ; k++)
                 maxN[j][(i + j) % m] = max(maxN[j][(i + j) % m] ,
                 maxN[j][k % m] + maxN[k % m][(i + j) % m] + num[j] * num[k % m] * num[(j + i) % m]);
      ; i < m ; i++)    maxAll = max(maxAll , maxN[i][i]);
     fast_print(maxAll);
     ;
 }

能量项链

 //依赖背包弱化版,直接枚举一棵依赖关系树里面的选择即可
 #include<bits/stdc++.h>
 using namespace std;
 struct ys{
     ] , wei[] , index;
 }ans[];
 ] , visa[];
 int main()
 {
     ;
     cin >> N >> M;
     N /= ;
      ; i <= M ; i++)
     {
         int a , b , c;
         cin >> a >> b >> c;
         a /= ;
         if(c)
         {
              ; i < dirA ; i++)
                 if(ans[i].index == c)
                 {
                     )
                     {
                         ans[i].wei[] = ans[i].wei[] + a;
                         ans[i].mon[] = ans[i].mon[] + a * b;
                     }
                     else
                     {
                         ans[i].wei[] = ans[i].wei[] + a;
                         ans[i].wei[] = ans[i].wei[] + a;
                         ans[i].mon[] = ans[i].mon[] + a * b;
                         ans[i].mon[] = ans[i].mon[] + a * b;
                     }
                     ans[i].dirN++;
                 }
         }
         else{
             ans[dirA].dirN = ;
             ans[dirA].mon[] = a * b;
             ans[dirA].wei[] = a;
             ans[dirA++].index = i;
         }
     }
      ; i < dirA ; i++)
     {
          ; j <= N ; j++)    visa[j] = vis[j];
          ; j <  && ans[i].mon[j] ; j++)
              ; k--)
                 visa[k + ans[i].wei[j]] = max(visa[k + ans[i].wei[j]] , vis[k] + ans[i].mon[j]);
          ; j <= N ; j++)    vis[j] = visa[j];
     }
     cout << vis[N] * ;
     ;
 }

金明的预算方案

 //递推,设f[i][j]表示从后往前第i位,数字为j时候的方案数,记得写高精
 #include<bits/stdc++.h>
 using namespace std;

 struct BigNum{
     ];

     BigNum(){
         memset(num ,  , sizeof(num));
     }

     void operator =(int k){
         while(k){
             num[++num[]] = k % ;
             k /= ;
         }
     }

     BigNum operator +(BigNum a){
         BigNum c;
         c.num[] = num[] > a.num[] ? num[] : a.num[];
          ; i <= c.num[] ; i++)
             ){
                 ++c.num[i + ];
                 c.num[i] -= ;
             }
         ] + ])
             ++c.num[];
         return c;
     }

     inline void output(){
         ])
             putchar(');
         ] ; i ; i--)
             putchar(num[i] + );
     }
 };

  ,  ,  ,  ,  ,  ,  ,  ,  , };
 BigNum sum , *ans[];

 int main()
 {
     int K , W;
     cin >> K >> W;
      ; i <= W / K +  ; i++)
         ans[i] = new BigNum[pow2[K]];
      ; i < pow2[K] ; i++)
         ans[][i] = ;
      ; (j - ) * K < W ; j++)
          ; k ; k--){
             ans[j][k] = ans[j][k + ] + ans[j - ][k + ];
             ) * K < W)
                 sum = sum + ans[j][k];
         }
     sum.output();
      ;
 }

2^k进制数

 //模拟题
 #include<bits/stdc++.h>
 //This code is written by Itst
 using namespace std;

 inline int read(){
     ;
     ;
     char c = getchar();
     while(c != EOF && !isdigit(c)){
         if(c == '-')
             f = ;
         c = getchar();
     }
     while(c != EOF && isdigit(c)){
         a = (a << ) + (a << ) + (c ^ ');
         c = getchar();
     }
     return f ? -a : a;
 }

 ] , to[][] , times[][] , need[] , spend[];
 ][];

 int main(){
 #ifdef OJ
     freopen("1065.in" , "r" , stdin);
     //freopen("1065.out" , "w" , stdout);
 #endif
     M = read();
     N = read();
     ;
      ; i <= N * M ; i++)
         need[i] = read();
      ; i <= N ; i++)
          ; j <= M ; j++)
             to[i][j] = read();
      ; i <= N ; i++)
          ; j <= M ; j++)
             times[i][j] = read();
      ; i <= N * M ; i++){
         in[need[i]]++;
          ; j++){
             ;
              ; f && k < times[need[i]][in[need[i]]] ; k++)
                 if(vis[to[need[i]][in[need[i]]]][j + k]){
                     f = ;
                     j = j + k;
                 }
             if(f){
                  ; k < times[need[i]][in[need[i]]] ; k++)
                     vis[to[need[i]][;
                 maxN = max(maxN , j + times[need[i]][in[need[i]]]);
                 spend[need[i]] = j + times[need[i]][in[need[i]]];
                 break;
             }
         }
     }
     cout << maxN;
     ;
 }

作业调度方案

NOIP2007(clear)

 //又要写高精...每一行是独立的,考虑区间DP,(倒序DP方式:)设f[i][j]表示最后选择i到j的最大得分,每一次枚举左右即可。
 #include<bits/stdc++.h>
 using namespace std;
 struct BN{
     ];
     int& operator [](int x){return num[x];}
     BN& operator =(const char *c){
          , k = ;
          ; i <= n ; i++){
             ) j++ , k = ;
                num[j] += k * (c[n - i] ^ );
             k = (k << ) + (k << );
         }
         num[] = j;
         return *this;
     }
     BN(){memset(num ,  , sizeof(num));}
     BN(const BN &a){memcpy(num , a.num , sizeof(num));}
     BN( , sizeof(num));*this = s;}
     BN operator +(BN a){
         BN c;
         c[] = max(a[] , num[]);
          ; i <= c[] ; i++)
             ){
                 c[i + ]++;
                 c[i] -= ;
             }
         ] + ])    ++c[];
         return c;
     }
     BN operator *(int a){
         BN c;
         c[] = num[];
          ; i <= num[] ; i++)
             c[i] = num[i] << ;
          ; i <= c[] ; i++)
             ){
                 c[i + ] += c[i] / ;
                 c[i] %= ;
             }
         ] + ])    c[]++;
         return c;
     }
 }maxN[][];
 inline BN input(){
     ] = {};
     scanf("%s" , c);
     return BN(c);
 }
 inline void output(BN n){
     printf(]]);
     ])    printf(]]);
 }
 inline BN max(BN a , BN b){
     ] > b[])    return a;
     ] < b[])    return b;
     ] ; i ; i--)
         if(a[i] > b[i])    return a;
         else    if(a[i] < b[i])    return b;
     return a;
 }
 int main(){
     BN sum;
     int N , M;
     for(scanf("%d%d" , &N , &M) ; N ; N--){
          ; i <= M ; i++)    maxN[i][i] = input();
          ; i ^ M ; i++)
              ; j + i <= M ; j++)
                 maxN[j][j + i] = max(maxN[j][j] + maxN[j + ][j + i] *  , maxN[j + i][j + i] + maxN[j][j + i - ] * );
         sum = sum + maxN[][M] * ;
     }
     output(sum);
     ;
 }

矩阵取数游戏

 //随你怎么写,不用桶排序就行
 #include<bits/stdc++.h>
 #define ll long long
 using namespace std;
 inline ll fast_read()
 {
     char c = getchar();
     ll a = ;
     ;
     while(!isdigit(c))
     {
         ;
         c = getchar();
     }
     ) + (a << ) + c - ' , c = getchar();
     return k ? -a : a;
 }
 inline void fast_print(ll x)
 {
     ] , dirN = -;
     )    putchar('-') , x = -x;
      , x /= ;
     )    putchar(');
     )    putchar(num[dirN--] + );
 }
 map < int , int > m;
 int main()
 {
     for(int n = fast_read() ; n ; n--)
         m[fast_read()]++;
     for(map < int , int >::iterator i = m.begin() ; i != m.end() ; i++)
     {
         fast_print(i -> first);
         putchar(' ');
         fast_print(i -> second);
         putchar('\n');
     }
     ;
 }

统计数字

 //模拟题,务必注意细节
 #include<bits/stdc++.h>
 using namespace std;
 int main()
 {
     ios::sync_with_stdio(false);
     int p1 , p2 , p3;
     string s;
     cin >> p1 >> p2 >> p3 >> s;
      ; i < s.size() ; i++)
         if(s[i] - '-')    cout << s[i];
         else{
             ] >= s[i + ] || !((s[i - ] >= ] >= ] >= ] >= ] <= ] <= ')))
                 cout << s[i];
             else
             {
                 string st;
                 ] +  ; k < s[i + ] ; k++)
                      ; j < p2 ; j++)    st += k;
                 )    reverse(st.begin() , st.end());
                 switch(p1)
                 {
                     :
                         cout << st;
                         break;
                     :
                     {
                          ; i < st.size() ; i++)
                             if(st[i] >= 'a')    st[i] -= 'a' - 'A';
                         cout << st;
                         break;
                     }
                     default:
                         cout << string(st.size() , '*');
                 }
             }
         }
     ;
 }

字符串的展开

 //进阶指南上面讲得很好啊qwq要在这里说要说很多所以就自行领悟吧qwq话说这道题的直径有很好的性质
 #include<bits/stdc++.h>
 #define LG
 //This code is written by Itst
 using namespace std;

 inline int read(){
     ;
     ;
     char c = getchar();
     while(c != EOF && !isdigit(c)){
         if(c == '-')
             f = ;
         c = getchar();
     }
     while(c != EOF && isdigit(c)){
         a = (a << ) + (a << ) + (c ^ ');
         c = getchar();
     }
     return f ? -a : a;
 }

 ;
 struct Edge{
     int end , upEd , w;
 }Ed[MAXN << ];
 ] , head[MAXN] , N , cntEd =  , maxLen , maxDir , cntRoute , sum;

 inline void addEd(int a , int b , int c){
     Ed[++cntEd].end = b;
     Ed[cntEd].upEd = head[a];
     Ed[cntEd].w = c;
     head[a] = cntEd;
 }

 void dfs(int now , int fa , int len){
     for(int i = head[now] ; i ; i = Ed[i].upEd)
         if(Ed[i].end != fa){
             pre[Ed[i].end] = i;
             dfs(Ed[i].end , now , len + Ed[i].w);
         }
     if(maxLen < len){
         maxLen = len;
         maxDir = now;
     }
 }

 void getRoute(int start , int end){
     while(end != start){
         route[++cntRoute][] = end;
         route[cntRoute][] = Ed[pre[end]].w;
         sum += Ed[pre[end]].w;
         end = Ed[pre[end] ^ ].end;
     }
     route[++cntRoute][] = start;
 }

 void Dfs(int now , int belong , int fa , int len){
     for(int i = head[now] ; i ; i = Ed[i].upEd)
         ][] && Ed[i].end != route[belong + ][])
             Dfs(Ed[i].end , belong , now , len + Ed[i].w);
     maxL[belong] = max(maxL[belong] , len);
 }

 int main(){
 #ifdef LG
     freopen("1099.in" , "r" , stdin);
     //freopen("1099.out" , "w" , stdout);
 #endif
     N = read();
     int S = read();
      ; i < N ; i++){
         int a = read() , b = read() , c = read();
         addEd(a , b , c);
         addEd(b , a , c);
     }
     dfs( ,  , );
     int t = maxDir;
     maxLen = ;
     dfs(t ,  , );
     getRoute(t , maxDir);
      , q =  , lenP =  , dis =  , lenQ = sum , maxAll =  , ans = 0x7fffffff;
      ; i <= cntRoute ; i++){
         Dfs(route[i][] , i ,  , );
         maxAll = max(maxAll , maxL[i]);
     }
     do{
         ] <= S){
             lenQ -= route[q][];
             dis += route[q++][];
         }
         ans = min(ans , max(maxAll , max(lenP , lenQ)));
         lenP += route[p][];
         dis -= route[p++][];
     }while(q < cntRoute);
     cout << ans;
     ;
 }

*树网的核

NOIP2008(clear)

//DP,设f[i][j][k]表示第一条路径走到(j,i-j),第二条路径走到(k,i-k)时的最大和,每一次枚举向右还是向下,注意路径不能相交
//当然写费用流也是可以的(逃
#include<bits/stdc++.h>
#define ll long long
using namespace std;
inline ll fast_read()
{
    char c = getchar();
    ll a = ;
    ;
    while(!isdigit(c))
    {
        ;
        c = getchar();
    }
    ) + (a << ) + c - ' , c = getchar();
    return k ? -a : a;
}
inline void fast_print(ll x)
{
    ] , dirN = -;
    )    putchar('-') , x = -x;
     , x /= ;
    )    putchar(');
    )    putchar(num[dirN--] + );
    putchar('\n');
}
][] , ans[][][];
int main()
{
    int M = fast_read() , N = fast_read();
     ; i <= M ; i++)
         ; j <= N ; j++)    num[i][j] = fast_read();
     ; i <= N + M ; i++)
         , i - M) ; k <= min(N , i - ) ; k++)
            ) ; l++)
            {
                ans[i][k][l] = max(ans[i - ][k][l] , max(ans[i - ][k][l - ] ,
                max(ans[i - ][k - ][l - ] , ans[i - ][k - ][l]))) + (k - l ? num[i - k][k] + num[i - l][l] : num[i - k][k]);
            }
    fast_print(ans[N + M][N][N]);
    ;
}

传纸条

 //按题意模拟
 #include<bits/stdc++.h>
 using namespace std;
 ];
 bool ifZ(int a)
 {
     )    return false;
      ; i * i <= a ; i++)
         )    return false;
     return true;
 }
 int main()
 {
     ios::sync_with_stdio(false);
     string s;
      , minN = ;
     cin >> s;
      ; i < s.size() ; i++)
         maxN = max(maxN , ++num[s[i] - 'a']);
      ; i <  ; i++)
         if(num[i] && num[i] < minN)        minN = num[i];
     if(ifZ(maxN - minN))    cout << "Lucky Word" << endl << maxN - minN;
     ;
     ;
 }

笨小猴

 //爆搜、打表都可以
 #include<bits/stdc++.h>
 using namespace std;
 inline int hcb(int a)
 {
     ;
     )
     {
         )
         {
             :
             :
             :    sum += ;break;
             :    sum += ;break;
             :    sum += ;break;
             :    sum += ;break;
             :    sum += ;break;
             ;
         }
         a /= ;
     }
     switch(a)
     {
         :
         :
         :    sum += ;break;
         :    sum += ;break;
         :    sum += ;break;
         :    sum += ;break;
         :    sum += ;break;
         ;
     }
     return sum;
 }
 int main()
 {
     ios::sync_with_stdio(false);
     ;
     cin >> n;
     n -= ;
      ; i <=  ; i++)
          ; j++)
             if(hcb(i) + hcb(j) + hcb(i + j) == n)
                 ;
                 else    cou++;
     cout << cou;
     ;
 }

火柴棒等式

 //贪心地对第一个栈进行操作,如果后面有只能加入第一个栈的数字才考虑将当前数字加入第二个栈
 #include<bits/stdc++.h>
 #define LG
 //This code is written by Itst
 using namespace std;

 inline int read(){
     ;
     ;
     char c = getchar();
     while(c != EOF && !isdigit(c)){
         if(c == '-')
             f = ;
         c = getchar();
     }
     while(c != EOF && isdigit(c)){
         a = (a << ) + (a << ) + (c ^ ');
         c = getchar();
     }
     return f ? -a : a;
 }

 ] , s2[] , num[] , top1 , top2 , cntStep , now;
 ];
 ];

 int main(){
 #ifdef LG
     freopen("1155.in" , "r" , stdin);
     //freopen("1155.out" , "w" , stdout);
 #endif
     int N = read();
     s1[] = s2[] = ;
      ; i <= N ; i++)
         num[i] = read();
      ; i <= N ; i++){
         ;
         memset(vis ,  , sizeof(vis));
          ;  j <= N ; j++)
             if(num[j] > s2[top2]){
                  ; f && k < num[i] ; k++)
                     if(!vis[k])
                         f = ;
                 break;
             }
             else
                 vis[num[j]] = ;
         if(f && s1[top1] > num[i]){
             s1[++top1] = num[i];
             step[++cntStep] = 'a';
             ){
                 ++now;
                 --top1;
                 step[++cntStep] = 'b';
             }
         }
         else{
             ){
                 ++now;
                 --top2;
                 step[++cntStep] = 'd';
             }
             if(s2[top2] < num[i]){
                 puts(");
                 ;
             }
             s2[++top2] = num[i];
             step[++cntStep] = 'c';
         }
     }
     while(top1 || top2)
         ){
             ++now;
             --top1;
             step[++cntStep] = 'b';
         }
         else{
             ++now;
             --top2;
             step[++cntStep] = 'd';
         }
      ; i <= cntStep ; i++){
         putchar(step[i]);
         putchar(' ');
     }
     ;
 }

*双栈排序

NOIP2009(clear)

 //细节多得不行!!!
 #include<bits/stdc++.h>
 using namespace std;
 ] , dy[];
 int main(){
     ios::sync_with_stdio(false);
     string s1 , s2 , s3;
     cin >> s1 >> s2 >> s3;
      ; i < s1.size() ; i++)
     {
          || dy[s2[i] - )
         {
             cout << "Failed";
             ;
         }
         mw[s1[i] - ;
         dy[s2[i] - ;
     }
      ; i <  ; i++)
         if(!mw[i] || !dy[i])
         {
             cout << "Failed";
             ;
         }
      ; i < s3.size() ; i++)
         cout << ();
     ;
 }

潜伏者

 //枚举质数,对于每个质数分类讨论考虑取值个数
 #include<bits/stdc++.h>
 using namespace std;
 ];
 ] , cnt;
 inline int getNum(long long &a , int i){
     ;
     ){
         a /= i;
         cnt++;
     }
     return cnt;
 }
 inline int min(int a , int b){return a < b ? a : b;}
 inline int max(int a , int b){return a > b ? a : b;}
 int main(){
      ; i <=  ; i++)
         if(!prime[i]){
             num[cnt++] = i;
              ; j++)
                 prime[i * j] = ;
         }
     long long l1 , r1 , l2 , r2 , N , a0 , a1 , b0 , b1;
     for(scanf("%lld" , &N) ; N ; N--){
         ;
         scanf("%lld%lld%lld%lld" , &a0 , &a1 , &b0 , &b1);
          ; i < cnt && a0 + a1 + b0 + b1 -  && sum ; i++){
             int f1 = getNum(a0 , num[i]) , f2 = getNum(a1 , num[i]);
             ;
             else    if(f1 > f2)    l1 = r1 = f2;
             ;
             f1 = getNum(b0 , num[i]);    f2 = getNum(b1 , num[i]);
              , r2 = f1;
             ;
             else    l2 = r2 = f2;
             l1 = max(l1 , l2);
             r1 = min(r1 , r2);
             )    sum = ;
             sum *= (r1 - l1 + );
         }
         ){
             int f1 = getNum(b0 , a0),    f2 = getNum(b1 , a0);
              , r2 = f1;
             ;
             else    l2 = r2 = f2;
             f2 = getNum(a1 , a0) , f1 = getNum(a0 , a0);
             ;
             else    if(f1 > f2)    l1 = r1 = f2;
             ;
             l1 = max(l1 , l2);
             r1 = min(r1 , r2);
             sum *= (r1 - l1 + );
         }
         ){
             int f1 = getNum(b0 , a1),    f2 = getNum(b1 , a1);
              , r2 = f1;
             ;
             else    l2 = r2 = f2;
             f1 = getNum(a0 , a1) , f2 = getNum(a1 , a1);
             ;
             else    if(f1 > f2)    l1 = r1 = f2;
             ;
             l1 = max(l1 , l2);
             r1 = min(r1 , r2);
             sum *= (r1 - l1 + );
         }
         ){
             int f1 = getNum(a0 , b0) , f2 = getNum(a1 , b0);
             ;
             else    if(f1 > f2)    l1 = r1 = f2;
             ;
             f2 = getNum(b1 , b0);    f1 = getNum(b0 , b0);
              , r2 = f1;
             ;
             else    l2 = r2 = f2;
             l1 = max(l1 , l2);
             r1 = min(r1 , r2);
             sum *= (r1 - l1 + );
         }
         ){
             int f1 = getNum(a0 , b1) , f2 = getNum(a1 , b1);
             ;
             else    if(f1 > f2)    l1 = r1 = f2;
             ;
             f1 = getNum(b0 , b1);    f2 = getNum(b1 , b1);
              , r2 = f1;
             ;
             else    l2 = r2 = f2;
             l1 = max(l1 , l2);
             r1 = min(r1 , r2);
             sum *= (r1 - l1 + );
         }
         printf("%lld\n" , sum);
     }
     ;
 }

*Hankson的趣味题

 //缩点+记忆化搜索
 #include<bits/stdc++.h>
 #define MAXN 100001
 using namespace std;
 inline int read(){
     ;
     char c = getchar();
     while(!isdigit(c))    c = getchar();
     ) + a + (c ^ ') , c = getchar();
     return a;
 }
 inline int min(int a , int b){return a < b ? a : b;}
 inline int max(int a , int b){return a > b ? a : b;}
 vector < int > Ed[MAXN] , Ed_SCC[MAXN];
 int Stack[MAXN] , inSCC[MAXN] , dfn[MAXN] , low[MAXN] , MAX[MAXN] , MIN[MAXN] , pri[MAXN];
 int ts , N , M , head , num , ans;
 bool vis[MAXN] , in[MAXN] , visSCC[MAXN];
 void findSCC(int a){
     Stack[++head] = a;
     vis[a] = ;
     dfn[a] = low[a] = ++ts;
      ; i < Ed[a].size() ; i++){
         if(!vis[Ed[a][i]])    findSCC(Ed[a][i]);
         else    if(!in[Ed[a][i]])    continue;
         low[a] = min(low[a] , low[Ed[a][i]]);
     }
     if(dfn[a] == low[a]){
         num++;
         do{
             ;
             inSCC[Stack[head]] = num;
             Ed_SCC[num].push_back(Stack[head]);
             MAX[num] = max(MAX[num] , pri[Stack[head]]);
             MIN[num] = min(MIN[num] , pri[Stack[head]]);
         }while(Stack[head--] != a);
     }
 }
 bool dfs(int a , int lowBuy){
     if(in[a])    return visSCC[a];
     ;
     ;
     lowBuy = min(lowBuy , MIN[a]);
      ; i < Ed_SCC[a].size() ; i++)
          ; j < Ed[Ed_SCC[a][i]].size() ; j++)
             if(inSCC[Ed[Ed_SCC[a][i]][j]] != a)
                 if(dfs(inSCC[Ed[Ed_SCC[a][i]][j]] , lowBuy)){
                     visSCC[a] = ;
                     MAX[a] = max(MAX[a] , MAX[inSCC[Ed[Ed_SCC[a][i]][j]]]);
                 }
     if(visSCC[a]){
         ans = max(ans , MAX[a] - lowBuy);
         ;
     }
     ;
 }
 int main(){
     N = read();
     M = read();
      ; i <= N ; i++)    pri[i] = read();
     while(M--){
         int a = read() , b = read() , c = read();
         Ed[a].push_back(b);
         )    Ed[b].push_back(a);
     }
     memset(MIN , 0x3f , sizeof(MIN));
      ; i <= N ; i++)
         if(!vis[i])    findSCC(i);
     dfs(inSCC[] , 0x3f3f3f3f);
      cout << ans;
     ;
 }

*最优贸易

 //需要比较强的剪枝
 #include<bits/stdc++.h>
 #define K num[i][j].num
 using namespace std;
 ;
 struct kuai{
     ] , qz;
     void init()
     {
         fs = ;
         memset(vis ,  , );
     }
 };
 kuai num[][];
 inline void add(int i , int j);
 inline void erase(int i , int j);
 void dfs(int i , int j);
 void find();
 int main(){
      ; i <  ; i++)
          ; j <  ; j++)
         {
             num[i][j].init();
             num[i][j].qz =  - max(abs(i - ) , abs(j - ));
         }
      ; i <  ; i++)
          ; j <  ; j++)
         {
             scanf("%d" , &K);
             if(K)
                 add(i , j);
         }
     find();
     cout << maxN;
     ;
 }
 inline void add(int i , int j)
 {
      ; k <  ; k++)
     {
         if(!num[i][k].vis[K])    num[i][k].fs--;
         num[i][k].vis[K]++;
         if(!num[k][j].vis[K])    num[k][j].fs--;
         num[k][j].vis[K]++;
     }
      *  ; m < i /  *  +  ; m++)
          *  ; n < j /  *  +  ; n++)
         {
             if(!num[m][n].vis[K])    num[m][n].fs--;
             num[m][n].vis[K]++;
         }
 }
 inline void erase(int i , int j)
 {
      ; k <  ; k++)
     {
         )    num[i][k].fs++;
         num[i][k].vis[K]--;
         )    num[k][j].fs++;
         num[k][j].vis[K]--;
     }
      *  ; m < i /  *  +  ; m++)
          *  ; n < j /  *  +  ; n++)
         {
             )    num[m][n].fs++;
                num[m][n].vis[K]--;
         }
 }
 void dfs(int i , int j)
 {
      ; k <=  ; k++)
         if(!num[i][j].vis[k])
         {
             K = k;
             add(i , j);
             find();
             erase(i , j);
             K = ;
         }
 }
 void find()
 {
      , minX =  , minY = ;
      ; i >=  && min -  ; i--)
          ; j >=  && min -  ; j--)
             if(!K && !num[i][j].fs)
                 return;
             else
                 if(min > num[i][j].fs && num[i][j].fs && !K)
                 {
                     min = num[i][j].fs;
                     minX = i;
                     minY = j;
                 }
     )
     {
         ;
          ; i <  ; i++)
              ; j <  ; j++)
                 numm += K * num[i][j].qz;
         maxN = max(maxN , numm);
     }
     else
         dfs(minX , minY);
 }

*靶形数独

NOIP2010(clear)

 //送分题
 #include<bits/stdc++.h>
 using namespace std;
 ];
 int main()
 {
      , n , m;
     for(cin >> m >> n ; n ; n--)
     {
         ;
         cin >> k;
          ; f && i < min(dirNum , m) ; i++)
             ;
         if(f)    num[dirNum++ % m] = k;
     }
     cout << dirNum;
     ;
 }

机器翻译

 //并查集or二分图
 #include<bits/stdc++.h>
 using namespace std;
 inline int read(){
     ;
     char c = getchar();
     while(!isdigit(c))    c = getchar();
     ) + (a << ) + (c ^ ') , c = getchar();
     return a;
 }
 struct ani{
     ][];
     int* operator [](int a){return father[a];}
     //0same,1dif
 }ans[];
 pair < int , int > find(int a , int b){
     ]][b][] ^ ans[a][b][]){
         pair < ] , ans[a][b][]);
         ans[a][b][] = t.first;
         ans[a][b][] = t.second;
     }
     ] , ans[a][b][]);
 }
 struct Ed{
     int a , b , wei;
 }now[];
 bool cmp(Ed a , Ed b){
     return a.wei > b.wei;
 }
 int main(){
     int N = read() , M = read();
      ; i <= N ; i++)
          ; j ^  ; j++){
             ans[i][j][] = i;
             ans[i][j][] = j;
         }
      ; i ^ M ; i++){
         now[i].a = read();
         now[i].b = read();
         now[i].wei = read();
     }
     sort(now , now + M , cmp);
      ; i < M ; i++){
         ) == find(now[i].b , )){
             cout << now[i].wei;
             ;
         }
          ; j ^  ; j++){
             pair < int , int > t1 = find(now[i].a , j) , t2 = find(now[i].b , !j);
             ans[t1.first][t1.second][] = t2.first;
             ans[t1.first][t1.second][] = t2.second;
             //cout << t1.first << " " << t1.second << endl << t2.first << " " << t2.second << endl;
         }
     }
     cout << ;
     ;
 }

关押罪犯

 //设f[i][j][k][l]为使用了i个1、j个2、k个3、l个4时的最大得分,随便转移,或者记忆化
 #include<bits/stdc++.h>
 #define ll long long
 using namespace std;
 inline ll fast_read()
 {
     char c = getchar();
     ll a = ;
     ;
     while(!isdigit(c))
     {
         ;
         c = getchar();
     }
     ) + (a << ) + c - ' , c = getchar();
     return k ? -a : a;
 }
 inline void fast_print(ll x)
 {
     ] , dirN = -;
     )    putchar('-') , x = -x;
      , x /= ;
     )    putchar(');
     )    putchar(num[dirN--] + );
     putchar('\n');
 }
 ] , kp[][][][] , pot[];
 int main()
 {
     ll N = fast_read() , M = fast_read();
      ; i < N ; i++)    score[i] = fast_read();
      ; i < M ; i++)
     {
         int q = fast_read();
         pot[q]++;
     }
      ; i <= pot[] ; i++)
          ; j <= pot[] ; j++)
              ; p <= pot[] ; p++)
                  ; q <= pot[] ; q++)
                 {
                      :  , j1 = j ? j -  :  , p1 = p ? p -  :  , q1 = q ? q -  : ;
                     kp[i][j][p][q] = max(kp[i1][j][p][q] , max(kp[i][j1][p][q] , max(kp[i][j][p1][q] , kp[i][j][p][q1]))) + score[i + j *  + p *  + q * ];
                 }
     fast_print(kp[pot[]][pot[]][pot[]][pot[]]);
     ;
 }

乌龟棋

*引水入城

NOIP2011(clear)

 //不要开10w*10w数组啊喂
 #include<bits/stdc++.h>
 using namespace std;
 ][];
 int main()
 {
     std::ios::sync_with_stdio(false);
     int n , a , b;
     cin >> n;
      ; i < n ; i++)
         cin >> c[i][] >> c[i][] >> c[i][] >> c[i][];
     cin >> a >> b;
      ; i +  ; i--)
         ] && a <= c[i][] + c[i][] && b >= c[i][] && b <= c[i][] + c[i][])
         {
             cout << i + ;
             ;
         }
     cout << -;
     ;
 }

铺地毯

 //将还没有一个在它后面的价格小于p的客栈的数量和已经有的客栈的数量统计下来,每一次来一个客栈更新一次并贡献答案
 #include<bits/stdc++.h>
 using namespace std;
 inline long long read(){
     ;
     char c = getchar();
     while(!isdigit(c))    c = getchar();
     ) + (a << ) + (c ^ ') , c = getchar();
     return a;
 }
 ][];
 int main(){
     ;
     while(n--){
         int a = read() , b = read();
         if(b <= p)
              ; i ^ k ; i++){
                 num[i][] += num[i][];
                 num[i][] = ;
             }
         sum += num[a][];
         ]++;
         ]++;
     }
     cout << sum;
     ;
 }

选择客栈

 //搜索,(因为似乎数据保证刚好$N$步完成)所以相同色块一定不动;如果存在色块数量为1or2就剪枝;因为左移优先级低,所以通过左移交换两个块一定不优
 #include<bits/stdc++.h>
 //This code is written by Itst
 using namespace std;

 inline int read(){
     ;
     ;
     char c = getchar();
     while(c != EOF && !isdigit(c)){
         if(c == '-')
             f = ;
         c = getchar();
     }
     while(c != EOF && isdigit(c)){
         a = (a << ) + (a << ) + (c ^ ');
         c = getchar();
     }
     return f ? -a : a;
 }

 ][] = {,,,-,,,-,};
 ][] , N , now[][] , num[];
 ][];

 void output(){
      ; i < N ; i++)
         printf(] , now[i][] , now[i][]);
     exit();
 }

 inline void drop(){
      ; i <  ; i++)
          ; j <  ; j++)
             if(col[i][j]){
                 ;
                  && !col[i][p]){
                     col[i][p] = col[i][p + ];
                     col[i][p + ] = ;
                     p--;
                 }
             }
 }

 inline bool search(){
     ;
     memset(vis ,  , sizeof(vis));
      ; i <  ; i++)
          ; j <  && col[i][j] ; j++)
             ] && col[i][j] == col[i][j + ])
                 vis[i][j] = vis[i][j + ] = vis[i][j + ] = ;
      ; i <  ; i++)
          ; j <  ; j++)
             ][j] && col[i][j] == col[i + ][j])
                 vis[i][j] = vis[i + ][j] = vis[i + ][j] = ;
      ; i <  ; i++)
          ; j <  ; j++)
             if(vis[i][j]){
                 num[col[i][j]]--;
                 f = ;
                 col[i][j] = ;
             }
     return f;
 }

 inline void maintain(){
     do{
         drop();
     }while(search());
 }

 void dfs(int step){
     ;
      ; i <=  ; i++)
          || num[i] == )
             return;
         else
             if(num[i])
                 cnt = ;
     if(!cnt){
         output();
         return;
     }
     if(step == N)
         return;
     ][] , tnum[];
     memcpy(t , col , sizeof(col));
     memcpy(tnum , num , sizeof(num));
      ; i <  ; i++)
          ; j <  ; j++)
              ; k >= - ; k -= )
                  && i + k <  && col[i][j] && col[i][j] != col[i + k][j] && (k ==  || !col[i + k][j])){
                     swap(col[i][j] , col[i + k][j]);
                     now[step][] = i;
                     now[step][] = j;
                     now[step][] = k;
                     maintain();
                     dfs(step + );
                     memcpy(col , t , sizeof(col));
                     memcpy(num , tnum , sizeof(tnum));
                 }
 }

 int main(){
 #ifdef LG
     freopen("1312.in" , "r" , stdin);
     //freopen("1312.out" , "w" , stdout);
 #endif
     N = read();
      ; i <  ; i++)
          ; j <  ; j++)
             if(!(col[i][j] = read()))
                 break;
             else
                 ++num[col[i][j]];
     dfs();
     puts("-1");
     ;
 }

*Mayan游戏

 //二项式定理
 #include<bits/stdc++.h>
 #define ll long long
 using namespace std;
 inline ll fast_read()
 {
     char c = getchar();
     ll a = ;
     ;
     while(!isdigit(c))
     {
         ;
         c = getchar();
     }
     ) + (a << ) + c - ' , c = getchar();
     return k ? -a : a;
 }
 inline void fast_print(ll x)
 {
     ] , dirN = -;
     )    putchar('-') , x = -x;
      , x /= ;
     )    putchar(');
     )    putchar(num[dirN--] + );
 }
 ll square[][] = {{}};
 int main()
 {
     ll a = fast_read() , b = fast_read() , k = fast_read() , n = fast_read() , m = fast_read() , num = ;
      ; i <= k ; i++)
     {
         square[i][] = ;
          ; j <= i ; j++)    square[i][j] = (square[i - ][j] + square[i - ][j - ]) % ;
     }
      ; i < n ; i++)    num = num * a % ;
      ; i < m ; i++)    num = num * b % ;
     fast_print(num * square[k][n] % );
     ;
 }

计算系数

 //二分+前缀和
 #include<bits/stdc++.h>
 #define MAXN 200001
 #define ll long long
 using namespace std;
 inline ll read(){
     ll a = ;
     char c = getchar();
     while(!isdigit(c))    c = getchar();
     ) + (a << ) + (c ^ ') , c = getchar();
     return a;
 }
 ll w[MAXN] , v[MAXN] , num[MAXN] , allV[MAXN] , N , M , S , qj[MAXN][];
 ll check(ll a){
      ; i <= N ; i++){
         num[i] = (w[i] >= a) + num[i - ];
         allV[i] = (w[i] >= a ? v[i] : ) + allV[i - ];
     }
     ;
      ; i <= M ; i++)
         sum += (num[qj[i][]] - num[qj[i][] - ]) * (allV[qj[i][]] - allV[qj[i][] - ]);
     return sum;
 }
 inline ll abss(ll a){ ? a : -a;}
 int main(){
      , minW = 0x3f3f3f3f;
     N = read();    M = read();    S = read();
      ; i <= N ; i++){
         w[i] = read() , v[i] = read();
         if(maxW < w[i])    maxW = w[i];
         if(minW > w[i])    minW = w[i];
     }
      ; i <= M ; i++)
         qj[i][] = read() , qj[i][] = read();
     ){
         ll mid = maxW + minW >> ;
         if(check(mid) >= S)    minW = mid;
         else    maxW = mid;
     }
     cout << min(abss(check(minW) - S) , abss(S - check(maxW)));
     ;
 }

*聪明的质检员

 //每一次贪心地选择能够影响更多人的地方
 #include<bits/stdc++.h>
 #define MAXN 1010
 using namespace std;

 int far[MAXN] , down[MAXN] , D[MAXN] , maxD[MAXN] , minT[MAXN] , N , M , K;
 long long ans;

 inline void get(){
     ;
      ; i <= N ; i++){
         ans += time * down[i];
         time = max(time , maxD[i]) + D[i];
     }
 }

 inline void work(){
     far[N] = N;
      ; i ; i--)
         far[i] = minT[i + ] > maxD[i + ] ? far[i + ] : i + ;
      , maxDir = ;
      ; i < N ; i++)
         if(D[i] && maxN < down[far[i]] - down[i]){
             maxN  = down[far[i]] - down[i];
             maxDir = i;
         }
     D[maxDir]--;
     ans -= maxN;
      ; i <= far[maxDir] ; i++)
         minT[i] = max(minT[i - ] , maxD[i - ]) + D[i - ];
 }

 int main(){
     cin >> N >> M >> K;
      ; i < N ; i++)
         cin >> D[i];
      ; i <= M ; i++){
         int T , A , B;
         cin >> T >> A >> B;
         maxD[A] = max(maxD[A] , T);
         down[B]++;
         ans -= T;
     }
     get();
      ; i <= N ; i++){
         down[i] += down[i - ];
         minT[i] = max(minT[i - ] , maxD[i - ]) + D[i - ];
     }
     while(K--)
         work();
     cout << ans;
     ;
 }

*观光公交

NOIP2012(clear)

 //直接模拟
 #include<bits/stdc++.h>
 #define ll long long
 using namespace std;
 inline ll fast_read()
 {
     char c = getchar();
     ll a = ;
     ;
     while(!isdigit(c))
     {
         ;
         c = getchar();
     }
     ) + (a << ) + c - ' , c = getchar();
     return k ? -a : a;
 }
 inline void fast_print(ll x)
 {
     ] , dirN = -;
     )    putchar('-') , x = -x;
      , x /= ;
     )    putchar(');
     )    putchar(num[dirN--] + );
     putchar('\n');
 }
 int main()
 {
     string a , b;
     cin >> a >> b;
      , la = a.size() , lb = b.size();
      ; i < lb ; i++ , dirA++)
     {
         char c = a[dirA % la];
         while(c != 'a' && c-- != 'A')
         {
             b[i]--;
              || b[i] == )    b[i] += ;
         }
     }
     cout << b;
     ;
 }

Vigenère 密码

 //根据邻项交换推贪心策略,排序后算答案
 #include<bits/stdc++.h>
 using namespace std;
 ] , allSum[] , maxN[];
 struct p{
     int l , r;
 }ans[];
 bool cmp(p a , p b)
 {
     return a.l * a.r < b.l * b.r;
 }
 void comp()
 {
     ] < maxN[])    return;
     ] == maxN[])
         ] ; i ; i--)
             if(d[i] < maxN[i])    return;
             else    if(d[i] > maxN[i])    break;
      ; i <= d[] ; i++)    maxN[i] = d[i];
 }
 inline int fast_read()
 {
     char ch = getchar();
      , k = ;
     while(!isdigit(ch)){
         ;
         ch = getchar();
     }
     ) + (a << ) + ch - ' , ch = getchar();
     return a;
 }
 int main()
 {
     int n = fast_read();
      ; i <= n ; i++)
         ans[i].l = fast_read() , ans[i].r = fast_read();
     ].l)
     {
         allSum[++allSum[]] = ans[].l % ;
         ans[].l /= ;
     }
     sort(ans +  , ans + n +  , cmp);
      ; i <= n ; i++)
     {
         memset(d ,  , sizeof(d));
          , sum = ;
         ] ; j ; j--)
         {
             sum = sum *  + allSum[j];
             if(sum >= ans[i].r)
             {
                 d[j] = sum / ans[i].r;
                 sum %= ans[i].r;
                 if(!f)
                 {
                     f = ;
                     d[] = j;
                 }
             }
         }
         comp();
          ; j <= allSum[] ; j++)
             allSum[j] *= ans[i].l;
          ; j <= allSum[] ; j++)
             )
             {
                 allSum[j + ] += allSum[j] / ;
                 allSum[j] %= ;
                 ])    allSum[]++;
             }
     }
     ] ; i ; i--)    cout << maxN[i];
     ;
 }

*国王游戏

*开车旅行

 //拓欧裸题
 #include<bits/stdc++.h>
 #define ll long long
 using namespace std;
 inline ll fast_read()
 {
     char c = getchar();
     ll a = ;
     ;
     while(!isdigit(c))
     {
         ;
         c = getchar();
     }
     ) + (a << ) + c - ' , c = getchar();
     return k ? -a : a;
 }
 void exGcd(int a , int b , int &x , int &y)
 {
     )    x =  / a , y = ;
     else
     {
            exGcd(b , a % b , x , y);
         int t = x;
         x = y;
         y = t - a / b * y;
     }
 }
 int main()
 {
     int a = fast_read() , b = fast_read() , c , d;
     exGcd(a , -b , c , d);
     )    c += b;
     cout << c % b;
     ;
 }

*同余方程

 //线段树这种常数极大的东西在CCF老人机上一定会被卡常数成95pts
 #include<bits/stdc++.h>
 using namespace std;
 ];
 inline int read(){
     ;
     char c = getchar();
     while(!isdigit(c))    c = getchar();
     ) + (a << ) + (c ^ ') , c = getchar();
     return a;
 }
 int cou , N;
 inline int min(int a , int b){
     return a < b ? a : b;
 }
 struct node{
     node *left , *right;
     int start , end , minN , minus_tag;
     node(){
         if(_s == _e)    minN = read();
         else{
             left = );
             right = ) +  , _e);
             minN = min(left->minN , right->minN);
         }
     }
     void change(int _s , int _e , int num){
         if(_s == start && _e == end)
             ){
                 cout << - << endl << cou;
                 exit();
             }
             else{
                 minN += num;
                 minus_tag += num;
                 return;
             }
         left->minN += minus_tag;
         right->minN += minus_tag;
         left->minus_tag += minus_tag;
         right->minus_tag += minus_tag;
         minus_tag = ;
         )    left->change(_s , _e , num);
         )    right->change(_s , _e , num);
         else{
             left->change(_s , start + end >>  , num);
             right->change((start + end >> ) +  , _e , num);
         }
         minN = min(left->minN , right->minN);
     }
 }*Tree;
 int main(){
     int N = read() , K = read();
     Tree =  , N);
      ; cou <= K ; cou++)
     {
         int a = read() , b = read() , c = read();
         Tree->change(b , c , -a);
     }
     cout << ;
     ;
 }

借教室

*疫情控制

NOIP2013(clear)

 //快速幂裸题
 #include<bits/stdc++.h>
 #define ll long long
 using namespace std;
 inline ll fast_read()
 {
     char c = getchar();
     ll a = ;
     ;
     while(!isdigit(c))
     {
         ;
         c = getchar();
     }
     ) + (a << ) + c - ' , c = getchar();
     return k ? -a : a;
 }
 inline void fast_print(ll x)
 {
     ] , dirN = -;
     )    putchar('-') , x = -x;
      , x /= ;
     )    putchar(');
     )    putchar(num[dirN--] + );
 }
 ] , circle;
 inline int fast_mi(int a)
 {
     ll num =  % circle , add = ;
     while(a)
     {
         )    add = add * num % circle;
         a >>= ;
         num = num * num % circle;
     }
     return add;
 }
 int main()
 {
     int k = fast_read() , t = fast_read();
     ])
     {
         num[circle] = t;
         t = (num[circle++] + m) % n;
     }
     fast_print(num[fast_mi(k)]);
     ;
 }

转圈游戏

 //离散化+逆序对(显然两个相对大小顺序一样的时候答案最优)
 #include<bits/stdc++.h>
 #define MAXN 100001
 using namespace std;
 inline int read(){
     ;
     char c = getchar();
     while(!isdigit(c))    c = getchar();
     ) + (a << ) + (c ^ ') , c = getchar();
     return a;
 }
 int num1[MAXN] , num2[MAXN] , lsh1[MAXN] , lsh2[MAXN] , tree[MAXN] , N = read();
 map < int , int > n1 , to2 , n2;
 inline  ? a : -a;}
 inline int lowbit(int a){return a & -a;}
 inline int getSum(int a){
     ;
     while(a){
         sum += tree[a];
         a -= lowbit(a);
     }
     return sum;
 }
 inline void add(int a){
     while(a <= N){
         tree[a]++;
         a += lowbit(a);
     }
 }
 int main(){
     ;
      ; i < N ; i++)    num1[i] = lsh1[i] = read();
      ; i < N ; i++)    num2[i] = lsh2[i] = read();
     sort(lsh1 , lsh1 + N);
      ; i < N ; i++)    n1[lsh1[i]] = i + ;
      ; i < N ; i++)    to2[n1.find(num1[i])->second] = i + ;
     sort(lsh2 , lsh2 + N);
      ; i < N ; i++)    n2[lsh2[i]] = i + ;
      ; i >=  ; i--){
         int t = to2.find(n2.find(num2[i])->second)->second;
         sum += getSum(t - );
         add(t);
     }
     cout << sum % ;
     ;
 }

*火柴排队

*货车运输

 //维护递增的单调栈
 #include<bits/stdc++.h>
 #define ll long long
 using namespace std;
 inline ll fast_read()
 {
     char c = getchar();
     ll a = ;
     ;
     while(!isdigit(c))
     {
         ;
         c = getchar();
     }
     ) + (a << ) + c - ' , c = getchar();
     return k ? -a : a;
 }
 inline void fast_print(ll x)
 {
     ] , dirN = -;
     )    putchar('-') , x = -x;
      , x /= ;
     )    putchar(');
     )    putchar(num[dirN--] + );
 }
 int sum , a;
 int main()
 {
     for(int n = fast_read() ; n ; n--)
     {
         int b = fast_read();
         if(a > b)    sum += a - b;
         a = b;
     }
     fast_print(sum + a);
     ;
 }

积木大赛

 //DP
 #include<bits/stdc++.h>
 #define ll long long
 using namespace std;
 inline ll fast_read()
 {
     char c = getchar();
     ll a = ;
     ;
     while(!isdigit(c))
     {
         ;
         c = getchar();
     }
     ) + (a << ) + c - ' , c = getchar();
     return k ? -a : a;
 }
 inline void fast_print(ll x)
 {
     ] , dirN = -;
     )    putchar('-') , x = -x;
      , x /= ;
     )    putchar(');
     )    putchar(num[dirN--] + );
 }
 ] , h2[];
 int main()
 {
      , dir2 = ;
     h2[] = h1[] = fast_read();
      ; i <= n ; i++)
     {
         int a = fast_read();
         ) %  ==  && h1[dir1] != a)
             h1[++dir1] = a;
         else    h1[dir1] = a;
         ) %  ==  && h2[dir2] != a)
             h2[++dir2] = a;
         else    h2[dir2] = a;
     }
     fast_print(max(dir1 , dir2));
     ;
 }

花匠

*华容道

NOIP2014(clear)

 //模拟
 #include<bits/stdc++.h>
 using namespace std;
 ][] , Na[] , Nb[];
 int main()
 {
     ios::sync_with_stdio(false);
     sf[][] = sf[][] = sf[][] = sf[][] = sf[][] = -;
     sf[][] = sf[][] = sf[][] = sf[][] = sf[][] = ;
     cin >> N >> a >> b;
      ; i < a ; i++)    cin >> Na[i];
      ; i < b ; i++)    cin >> Nb[i];
     while(N--)
     {
         if(Na[dirA] - Nb[dirB])
             if(sf[Na[dirA]][Nb[dirB]])
                 )    sumA++;
                 else    sumB++;
             )    sumB++;
                 else    sumA++;
         dirA = (dirA + ) % a;
         dirB = (dirB + ) % b;
     }
     cout << sumA << " " << sumB;
     ;
 }

生活大爆炸版石头剪刀布

 //一棵树上只有可能出现:爷爷和孙子(?)和同父兄弟这两种情况会产生联合权值,第二种权值的计算需要优化成O(n)
 #include<bits/stdc++.h>
 using namespace std;
 inline int read(){
     register ;
     register char c = getchar();
     while(!isdigit(c))    c = getchar();
     ) + (a << ) + (c ^ ') , c = getchar();
     return a;
 }
 inline int max(int a , int b){
     return a > b ? a : b;
 }
 struct Edge{
     int upEd , end;
 }now[];
 ] , Las[];
 ];
 struct node{
     int num , father , grandpa;
 }ans;
 int main(){
     ;
     register ;
      ; i ^ n ; i++){
         a = read();
         b = read();
         now[(i << ) - ].end = b;
         now[(i << ) - ].upEd = Las[a];
         Las[a] = (i << ) - ;
         now[i << ].end = a;
         now[i << ].upEd = Las[b];
         Las[b] = i << ;
     }
      ; i ^ n +  ; i++)    num[i] = read();
     queue < node > q;
     ans.num = ;
     ans.father = ans.grandpa = ;
     q.push(ans);
     while(!q.empty()){
         ans = q.front();
         q.pop();
         if(ans.grandpa){
             sum += num[ans.grandpa] * num[ans.num] << ;
             maxN = max(maxN , num[ans.grandpa] * num[ans.num]);
         }
         vis[ans.num] = ;
         node ans1;
         ans1.grandpa = ans.father;
         ans1.father = ans.num;
         register  , maxM2 = ;
          , sumN = ;
         for(register int i = Las[ans.num] ; i ; i = now[i].upEd)
             if(!vis[now[i].end]){
                 if(num[now[i].end] > maxM1){
                     maxM2 = maxM1;
                     maxM1 = num[now[i].end];
                 }
                 else    if(num[now[i].end] > maxM2)    maxM2 = num[now[i].end];
                 sumM += num[ans1.num = now[i].end];
                 sumN += num[now[i].end] * num[now[i].end];
                 q.push(ans1);
             }
         maxN = max(maxN , maxM1 * maxM2);
         sum += sumM * sumM - sumN;
     }
     printf();
     ;
 }

*联合权值

 //DP
 #include<bits/stdc++.h>
 using namespace std;
 inline int read(){
     ;
     char c = getchar();
     while(!isdigit(c))
         c = getchar();
     while(isdigit(c)){
         a = (a << ) + (a << ) + (c ^ ');
         c = getchar();
     }
     return a;
 }
 inline int min(int a , int b){
     return a < b ? a : b;
 }
 struct gd{
     int P , L , R;
 }now[];
 bool cmp(gd a , gd b){
     return a.P < b.P;
 }
 ][] , minN[][];
 int main(){
     ;
     cin >> N >> M >> K;
      ; i <= N ; i++){
         jump[i][] = read();
         jump[i][] = read();
     }
      ; i <= K ; i++){
         now[i].P = read();
         now[i].L = read();
         now[i].R = read();
     }
     sort(now +  , now + K +  , cmp);
      ; i <= N ; i++){
         memset(minN[i & ] , ]));
          ; j <= M ; j++)
             minN[i & ][j + jump[i][] > M ? M : j + jump[i][]] = min(minN[i & ][j + jump[i][] > M ? M : j + jump[i][]] , min(minN[i & ][j] , minN[i &  ^ ][j]) + );
         ] +  ; j <= M ; j++)
             minN[i & ][j - jump[i][]] = min(minN[i & ][j - jump[i][]] , minN[i &  ^ ][j]);
         if(now[dir].P == i){
              ; j <= now[dir].L ; j++)
                 minN[i & ][j] = 0x3f3f3f3f;
             for(int j = now[dir].R ; j <= M ; j++)
                 minN[i & ][j] = 0x3f3f3f3f;
             ;
              ; j < now[dir].R && !f ; j++)
                 ][j] != 0x3f3f3f3f)
                     f = ;
             if(!f){
                 cout <<  << endl << dir - ;
                 ;
             }
             dir++;
         }
     }
     int ans = 0x3f3f3f3f;
      ; i <= M ; i++)
         ans = min(ans , minN[N & ][i]);
     cout <<  << endl << ans;
     ;
 }

*飞扬的小鸟

 //乱搞
 #include<bits/stdc++.h>
 using namespace std;
 ][];
 int main(){
     ios::sync_with_stdio(false);
      , d , n;
     ;
     cin >> d >> n;
      ; i < n ; i++)
     {
         int a , b , c;
         cin >> a >> b >> c;
         m[a][b] = c;
     }
      ; i <  ; i++)
          ; j <  ; j++)
         {
             ;
             ) ; k <= i + d ; k++)
                 ) ; p <= j + d ; p++)
                     num += m[k][p];
             if(num > maxN){
                 maxN = num;
                 cou = ;
             }
             else    if(num == maxN)    cou++;
         }
     cout << cou << " " << maxN;
     ;
 }

无线网络发射器选址

 //每一次预处理出无法到达终点的点并影响可以到达的点,然后最短路
 #include<bits/stdc++.h>
 using namespace std;
 inline int read(){
     ;
     char c = getchar();
     while(!isdigit(c))    c = getchar();
     ) + (a << ) + (c ^ ') , c = getchar();
     return a;
 }
 vector < ] , FanEd[];
 ] , vis2[];
 int main(){
     ios::sync_with_stdio();cin.tie();cout.tie();
     int n = read() , m = read();
     while(m--){
         int a = read() , b = read();
         Ed[a].push_back(b);
         FanEd[b].push_back(a);
     }
      ; i <= n ; i++)    vis2[i] = ;
     int st = read() , end = read();
     vis[end] = ;
     queue < int > q1;
     q1.push(end);
     while(!q1.empty()){
         int t = q1.front();
         q1.pop();
          ; i ^ FanEd[t].size() ; i++)
             if(!vis[FanEd[t][i]]){
                 vis[FanEd[t][i]] = ;
                 q1.push(FanEd[t][i]);
             }
     }
      ; i <= n ; i++)
         if(!vis[i]){
             vis2[i] = ;
              ; j ^ FanEd[i].size() ; j++)
                 vis2[FanEd[i][j]] = ;
         }
     if(!vis2[st]){
         cout << -;
         ;
     }
     queue < pair < int , int > > q;
     q.push(make_pair(st , ));
     while(!q.empty()){
         pair < int , int > t = q.front();
         q.pop();
          ; i ^ Ed[t.first].size() ; i++)
             if(vis2[Ed[t.first][i]]){
                 vis2[Ed[t.first][i]] = ;
                 if(Ed[t.first][i] == end){
                     cout << t.second + ;
                     ;
                 }
                 q.push(make_pair(Ed[t.first][i] , t.second + ));
             }
     }
     cout << -;
     ;
 }

寻找道路

 //998244353真是个好质数
 #include<bits/stdc++.h>
 #define MOD 998244353
 #define ll long long
 using namespace std;
 inline ll read(){
     ll a = ;
     char c = getchar();
     ;
     while(!isdigit(c)){
         if(c == '-')
             f = ;
         c = getchar();
     }
     while(isdigit(c)){
         a = ((a << ) + (a << ) + (c ^ ')) % MOD;
         c = getchar();
     }
     return f ? -a : a;
 }

 ];
 inline void print(int a){
     ;
     while(a){
         output[dirN++] = a % ;
         a /= ;
     }
     if(!dirN)
         putchar(');
     while(dirN)
         putchar(output[--dirN] + );
     putchar('\n');
 }

 ] , num[] , n , m;

 inline void calc(int dir){
     ll sum = num[n];
      ; i >=  ; i--)
         sum = (sum * dir + num[i]) % MOD;
     if(!sum)
         ans[++ans[]] = dir;
 }

 int main(){
     n = read();
     m = read();
      ; i <= n ; i++)
         num[i] = read();
      ; i <= m ; i++)
         calc(i);
      ; i <= ans[] ; i++)
         print(ans[i]);
     ;
 }

*解方程

NOIP2015(clear)

 //模拟
 #include<bits/stdc++.h>
 using namespace std;
 ][];
 int main()
 {
     int N;
     cin >> N;
      , j =  + N / ;
     num[i][j] = ;
      ; k <= N * N ; k++)
     {
          && j == N)    i++;
         ){
             i = N;
             j++;
         }
         else    if(j == N){
             j = ;
             i--;
         }][j + ]){
             i--;
             j++;
         }
         else    i++;
         num[i][j] = k;
     }
      ; i <= N ; i++)
     {
          ; j <= N ; j++)
             cout << num[i][j] << " ";
         cout << endl;
     }
     ;
 }

神奇的幻方

 //tarjan可以用来判环长哦!
 //这下面是一个古老的Kosaraju
 #include<bits/stdc++.h>
 #define ll long long
 #define MAXN 200001
 using namespace std;
 inline ll fast_read()
 {
     char c = getchar();
     ll a = ;
     ;
     while(!isdigit(c))
     {
         ;
         c = getchar();
     }
     ) + (a << ) + c - ' , c = getchar();
     return k ? -a : a;
 }
 inline void fast_print(ll x)
 {
     ] , dirN = -;
     )    putchar('-') , x = -x;
      , x /= ;
     )    putchar(');
     )    putchar(num[dirN--] + );
 }
 int num[MAXN] , fanNum[MAXN] , zhan[MAXN] , minN = MAXN , N = fast_read() , dirZ;
 bool vis[MAXN];
 struct edge{
     int end , upEd;
     void init(int a , int b)
     {
         upEd = fanNum[a];
         fanNum[a] = end = b;
     }
 }ans[MAXN];
 void fanDfs(int k)
 {
     vis[k] = ;
     for(int i = fanNum[k] ; i ; i = ans[i].upEd)
         if(!vis[ans[i].end])    fanDfs(ans[i].end);
     zhan[dirZ++] = k;
 }
 int dfs(int k)
 {
     vis[k] = ;
      + dfs(num[k]);
     ;
 }
 int main()
 {
      ; i <= N ; i++)
     {
         num[i] = fast_read();
         if(i == num[i])    {
             cout << ;
             ;
         }
         ans[i].init(num[i] , i);
     }
      ; i <= N ; i++)
         if(!vis[i])    fanDfs(i);
     memset(vis ,  , sizeof(vis));
      ; dirZ--)
         if(!vis[zhan[dirZ]])
         {
             int k = dfs(zhan[dirZ]);
             )    minN = min(minN , k);
         }
     fast_print(minN);
     ;
 }

信息传递

 //搜顺子,散排直接DP
 #include<bits/stdc++.h>
 //This code is written by Itst
 using namespace std;

 inline int read(){
     ;
     ;
     char c = getchar();
     while(c != EOF && !isdigit(c)){
         if(c == '-')
             f = ;
         c = getchar();
     }
     while(c != EOF && isdigit(c)){
         a = (a << ) + (a << ) + (c ^ ');
         c = getchar();
     }
     return f ? -a : a;
 }

 ] , gui[] , dp[][][][][] , ans;

 inline void sub(int step){
     ;
     ] = {};
      ; i <=  ; i++)
         ++num[pot[i]];
     ] && gui[]){
         ifGui = ;
         num[] += ;
     }
     else
         ] + gui[])
             num[]++;
     ans = min(ans , dp[num[]][num[]][num[]][num[]][ifGui] + step);
 }

 void dfs(int now , int step){
     if(step > ans)
         return;
     ){
         sub(step);
         return;
     }
      && pot[now + ] >= ){
         pot[now] -= ;
         ;
          && pot[i] >= ){
             pot[i++] -= ;
             dfs(now , step + );
         }
         while(--i >= now)
             pot[i] += ;
     }
      && pot[now + ] >=  && pot[now + ] >= ){
         pot[now] -= ;
         pot[now + ] -= ;
         ;
          && pot[i] >= ){
             pot[i++] -= ;
             dfs(now , step + );
         }
         while(--i >= now)
             pot[i] += ;
     }
     int i = now;
     while(pot[i]){
         )
             break;
         --pot[i++];
         )
             dfs(now , step + );
     }
     while(--i >= now)
         ++pot[i];
     dfs(now +  , step);
 }

 void init_dp(){
      ; m <=  ; m++)
          ; k + m <=  ; k++)
              ; j + k + m <=  ; j++)
                  ; i + j + k + m <=  ; i++)
                      ; i + j *  + k *  + m *  <=  && n <=  && (n ==  || i >= ) ; n++)
                         if(i + j + k + m){
                             ] = {i , j , k , m};
                             if(n)
                                 dp[i][j][k][m][n] = min(dp[i][j][k][m][n] , dp[i - ][j][k][m][]);
                             if(m){
                                 --num[];
                                  ; p <=  ; p++)
                                     if(num[p]){
                                         --num[p];
                                         if(p)
                                             ++num[p - ];
                                          ; q <=  ; q++)
                                             if(num[q]){
                                                 --num[q];
                                                 if(q)
                                                     ++num[q - ];
                                                 dp[i][j][k][m][n] = min(dp[i][j][k][m][n] , dp[num[]][num[]][num[]][num[]][num[] >=  && n]);
                                                 if(q)
                                                     --num[q - ];
                                                 ++num[q];
                                             }
                                         ++num[p];
                                         if(p)
                                             --num[p - ];
                                     }
                                  ; p <=  ; p++)
                                     if(num[p]){
                                         --num[p];
                                         )
                                             ++num[p - ];
                                          ; q <=  ; q++)
                                             if(num[q]){
                                                 --num[q];
                                                 )
                                                     ++num[q - ];
                                                 dp[i][j][k][m][n] = min(dp[i][j][k][m][n] , dp[num[]][num[]][num[]][num[]][num[] >=  && n]);
                                                 )
                                                     --num[q - ];
                                                 ++num[q];
                                             }
                                         ++num[p];
                                         )
                                             --num[p - ];
                                     }
                                 ++num[];
                             }
                              ; a <=  ; a++)
                                 if(num[a]){
                                     --num[a];
                                     )
                                         ++num[];
                                      ; p <=  ; p++)
                                         if(num[p]){
                                             --num[p];
                                             if(p)
                                                 ++num[p - ];
                                             dp[i][j][k][m][n] = min(dp[i][j][k][m][n] , dp[num[]][num[]][num[]][num[]][num[] >=  && n]);
                                             if(p)
                                                 --num[p - ];
                                             ++num[p];
                                         }
                                      ; p <=  ; p++)
                                         if(num[p]){
                                             --num[p];
                                             )
                                                 ++num[p - ];
                                             dp[i][j][k][m][n] = min(dp[i][j][k][m][n] , dp[num[]][num[]][num[]][num[]][num[] >=  && n]);
                                             ++num[p];
                                             )
                                                 --num[p - ];
                                         }
                                     )
                                         --num[];
                                     ++num[a];
                                 }
                              ; p ; p--)
                                  ; q <=  ; ++q)
                                     if(num[q]){
                                         --num[q];
                                         if(q >= p)
                                             ++num[q - p];
                                         dp[i][j][k][m][n] = min(dp[i][j][k][m][n] , dp[num[]][num[]][num[]][num[]][num[] >=  && n]);
                                         if(q >= p)
                                             --num[q - p];
                                         ++num[q];
                                     }
                             ++dp[i][j][k][m][n];
                         }
 }

 int main(){
 #ifdef LG
     freopen("2668.in" , "r" , stdin);
     //freopen("2668.out" , "w" , stdout);
 #endif
     memset(dp , 0x3f , sizeof(dp));
     dp[][][][][] = ;
     init_dp();
     int T = read() , N = read();
      ; i <= T ; i++){
         memset(pot ,  , sizeof(pot));
         gui[] = gui[] = ;
         ans = 0x7fffffff;
          ; j <= N ; j++){
             int a = read();
             if(a){
                 ++pot[a <=  ? a +  : a - ];
                 read();
             }
             else
                 ++gui[read()];
         }
         dfs( , );
         printf("%d\n" , ans);
     }
     ;
 }

*斗地主

 //二分+贪心
 #include<bits/stdc++.h>
 #define ll long long
 using namespace std;
 inline ll fast_read()
 {
     char c = getchar();
     ll a = ;
     ;
     while(!isdigit(c))
     {
         ;
         c = getchar();
     }
     ) + (a << ) + c - ' , c = getchar();
     return k ? -a : a;
 }
 inline void fast_print(ll x)
 {
     ] , dirN = -;
     )    putchar('-') , x = -x;
      , x /= ;
     )    putchar(');
     )    putchar(num[dirN--] + );
 }
 ];
 int main()
 {
      , t = L + ;
     num[M + ] = L;
      ; i <= M ; i++)    num[i] = fast_read();
     )
     {
          , cou =  , befL = ;
          ; i <= M +  ; i++)
             if(num[i] - befL < mid)    cou++;
             else    befL = num[i];
         if(cou > N)    t = mid;
         else    h = mid;
     }
     fast_print(h);
     ;
 }

跳石头

 //DP
 #include<bits/stdc++.h>
 #define MOD 1000000007
 using namespace std;
 ][][];
 vector < ];
 int main(){
     int N , M , K;
     string s , cmp;
     cin >> N >> M >> K >> s >> cmp;
     bp[][][] = ;
      ; i >=  ; i--)
         v[cmp[i] - 'a'].push_back(i);
      ; i < N ; i++){
          ; j <= M ; j++)
              ; k <= K ; k++)
                 bp[][j][k] = (bp[][j][k] + bp[][j][k]) % MOD;
         memcpy(bp[] , bp[] , ]));
         memset(bp[] ,  , ]));
          ; j < v[s[i] - 'a'].size() ; j++)
             for(int k = K ; k ; k--)
                 bp[][v[s[i] - ][k] = ((bp[][v[s[i] - ][v[s[i] - ]) % MOD + bp[][v[s[i] - ]) % MOD;
     }
     cout << ((bp[][M][K] + bp[][M][K]) % MOD + bp[][M][K]) % MOD;
     ;
 }

子串

 //删掉一条边的影响一定只会在前i条路径上(i极大),所以从大到小在树上加边,每一次找到在所有最长的路径上的边中权值最大的边尝试删除。
 #include<bits/stdc++.h>
 #define MAXN 300002
 #define l(x) Tree[x].l
 #define r(x) Tree[x].r
 #define sum(x) Tree[x].sum
 #define mark(x) Tree[x].mark
 #define mid(x) (Tree[x].l + Tree[x].r >> 1)
 #define maxMark(dir) Tree[dir].maxMark
 #define maxNum(dir) Tree[dir].maxNum
 using namespace std;

 struct node{
     int l , r , sum , mark , maxMark , maxNum;
 }Tree[MAXN << ];
 struct Edge{
     int end , w , upEd;
 }Ed[MAXN << ];
 struct route{
     int start , end , w;
 }Now[MAXN];
 int head[MAXN] , val[MAXN] , size[MAXN] , fa[MAXN] , son[MAXN] , dep[MAXN];
 int N , M , cntEd , ts , top[MAXN] , ind[MAXN] , rk[MAXN];

 bool cmp(route a , route b){
     return a.w > b.w;
 }

 inline int max(int a , int b){
     return a > b ? a : b;
 }

 inline void addEd(int a , int b , int c){
     Ed[++cntEd].end = b;
     Ed[cntEd].w = c;
     Ed[cntEd].upEd = head[a];
     head[a] = cntEd;
 }

 void dfs1(int dir , int father , int v){
     val[dir] = v;
     size[dir] = ;
     dep[dir] = dep[fa[dir] = father] + ;
     for(int i = head[dir] ; i ; i = Ed[i].upEd)
         if(fa[dir] != Ed[i].end){
             dfs1(Ed[i].end , dir , Ed[i].w);
             size[dir] += size[Ed[i].end];
             if(size[son[dir]] < size[Ed[i].end])
                 son[dir] = Ed[i].end;
         }
 }

 void dfs2(int dir , int t){
     top[dir] = t;
     rk[ind[dir] = ++ts] = dir;
     if(!son[dir])
         return;
     dfs2(son[dir] , t);
     for(int i = head[dir] ; i ; i = Ed[i].upEd)
         if(Ed[i].end != son[dir] && Ed[i].end != fa[dir])
             dfs2(Ed[i].end , Ed[i].end);
 }

 inline void pushup(int dir , int maxN){
     ) , maxMark(dir <<  | )))
         maxNum(dir) = max(maxNum(dir) , maxN);
     else{
         maxMark(dir) = max(maxMark(dir << ) , maxMark(dir <<  | ));
         maxNum(dir) = maxN;
     }
 }

 inline void pushdown(int dir){
     mark(dir << ) += mark(dir);
     mark(dir <<  | ) += mark(dir);
     maxMark(dir << ) += mark(dir);
     maxMark(dir <<  | ) += mark(dir);
     mark(dir) = ;
 }

 void init(int l , int r , int dir){
     l(dir) = l;
     r(dir) = r;
     if(l == r)
         sum(dir) = maxNum(dir) = val[rk[l]];
     else{
         init(l , mid(dir) , dir << );
         init(mid(dir) +  , r , dir <<  | );
         sum(dir) = sum(dir << ) + sum(dir <<  | );
         maxNum(dir) = max(maxNum(dir << ) , maxNum(dir <<  | ));
     }
 }

 int getSum(int l , int r , int dir){
     if(l(dir) >= l && r(dir) <= r)
         return sum(dir);
     ;
     if(l <= mid(dir))
         sum += getSum(l , r , dir << );
     if(r > mid(dir))
         sum += getSum(l , r , dir <<  | );
     return sum;
 }

 int getMark(int l , int r , int dir , int now){
     if(l(dir) >= l && r(dir) <= r){
         mark(dir)++;
         ;
     }
     pushdown(dir);
     ;
     if(l <= mid(dir))
         maxN = max(maxN , getMark(l , r , dir <<  , now));
     if(r > mid(dir))
         maxN = max(maxN , getMark(l , r , dir <<  |  , now));
     if(maxN)
         pushup(dir , maxN);
     return maxN;
 }

 inline void work1(int dir){
     int x = Now[dir].start , y = Now[dir].end , tx = top[x] , ty = top[y];
     while(tx != ty)
         if(dep[tx] >= dep[ty]){
             Now[dir].w += getSum(ind[tx] , ind[x] , );
             x = fa[tx];
             tx = top[x];
         }
         else{
             Now[dir].w += getSum(ind[ty] , ind[y] , );
             y = fa[ty];
             ty = top[y];
         }
     if(ind[x] < ind[y])
         Now[dir].w += getSum(ind[x] +  , ind[y] , );
     if(ind[x] > ind[y])
         Now[dir].w += getSum(ind[y] +  , ind[x] , );
 }

 inline int work2(int dir){
     ;
     while(tx != ty)
         if(dep[tx] >= dep[ty]){
             maxN = max(maxN , getMark(ind[tx] , ind[x] ,  , dir));
             x = fa[tx];
             tx = top[x];
         }
         else{
             maxN = max(maxN , getMark(ind[ty] , ind[y] ,  , dir));
             y = fa[ty];
             ty = top[y];
         }
     if(ind[x] < ind[y])
         maxN = max(maxN , getMark(ind[x] +  , ind[y] ,  , dir));
     if(ind[x] > ind[y])
         maxN = max(maxN , getMark(ind[y] +  , ind[x] ,  , dir));
     return maxN;
 }

 int main(){
     srand((unsigned)time());
     scanf("%d%d" , &N , &M);
      ; i < N ; i++){
         int a , b , c;
         scanf("%d%d%d" , &a , &b , &c);
         addEd(a , b , c);
         addEd(b , a , c);
     }
     ;
     dfs1(S ,  , );
     dfs2(S , S);
     init( , N , );
      ; i <= M ; i++){
         scanf("%d%d" , &Now[i].start , &Now[i].end);
         work1(i);
     }
     sort(Now +  , Now + M +  , cmp);
      , minN = ;
     while(dir <= M){
         int t = work2(dir);
         ].w <= Now[].w - t){
             minN = min(minN , Now[].w - t);
             break;
         }
         minN = Now[dir + ].w;
         dir++;
     }
     cout << minN;
     ;
 }

*运输计划

NOIP2016(clear)

 //有点绕的模拟
 #include<bits/stdc++.h>
 using namespace std;
 ];
 ];
 int main()
 {
     ios::sync_with_stdio(false);
     ;
     cin >> n >> m;
      ; i < n ; i++)    cin >> cx[i] >> name[i];
     while(m)
     {
         int a , b;
         cin >> a >> b;
         )    dir = (dir + b) % n;
         else    dir = (dir - b + n) % n;
         m--;
     }
     cout << name[dir];
     ;
 }

玩具谜题

 //期望DP
 #include<bits/stdc++.h>
 #define MAXN 2001
 using namespace std;
 ] , gl[MAXN];
 ] , route[][] , n , m , v , e;

 inline double calc(int dir , bool f1 , bool f2){
     ;
      ; i <= f1 ; i++)
          ; j <= f2 ; j++)
             sum += route[room[dir - ][i]][room[dir][j]] * (f1 ? (i ? gl[dir - ] :  - gl[dir - ]) : ) * (f2 ? (j ? gl[dir] :  - gl[dir]) : );
     return sum;
 }

 int main(){
     ios::sync_with_stdio();
     cin.tie();
     cout.tie();
     cin >> n >> m >> v >> e;
     ){
         cout << ) << 0.00;
         ;
     }
      ; i <= n ; i++)
         cin >> room[i][];
      ; i <= n ; i++)
         cin >> room[i][];
      ; i <= n ; i++)
         cin >> gl[i];
     memset(route , 0x3f , sizeof(route));
     while(e--){
         int a , b , c;
         cin >> a >> b >> c;
         route[a][b] = route[b][a] = min(route[a][b] , c);
     }
      ; k <= v ; k++){
         route[k][k] = ;
          ; i <= v ; i++)
              ; j <= v ; j++)
                 route[i][j] = min(route[i][j] , route[i][k] + route[k][j]);
     }
     double minN = 0x7fffffff;
     memset(minQW , 0x7f , sizeof(minQW));
     minQW[][] = minQW[][] = ;
      ; i <= n ; i++){
          ; j--){
             minQW[j][] = min(minQW[j][] + calc(i ,  , ) , minQW[j][] + calc(i ,  , ));
             if(j)
                 minQW[j][] = min(minQW[j - ][] + calc(i ,  , ) , minQW[j - ][] + calc(i ,  , ));
         }
     }
      ; i <= m ; i++)
         minN = min(minN , min(minQW[i][] , minQW[i][]));
     cout << ) << minN;
     ;
 }

*换教室

 //组合数+二维前缀和
 #include<bits/stdc++.h>
 using namespace std;
 ][] , all[][];
 int main(){
     ios::sync_with_stdio();
     int t , k;
     cin >> t >> k;
      ; i <=  ; i++)
          ; j <= i ; j++)
         {
              || j == i)    num[i][j] = ;
             ][j] + num[i - ][j - ]) % k;
             ;
         }
      ; i <=  ; i++)
          ; j <=  ; j++)    all[i][j] += all[i][j - ];
      ; i <=  ; i++)
          ; j <=  ; j++)    all[i][j] += all[i - ][j];
     while(t--){
         int a , b;
         cin >> a >> b;
         cout << all[a][b] << endl;
     }
     ;
 }

组合数问题

 //队列优化堆
 #include<bits/stdc++.h>
 using namespace std;

  , inf =  << ;
 ][MAXN] , n , m , u , v , q , t , hd[] , tl[];

 inline int top(){
     ;
      ; i <  ; i++)
         if(hd[i] != tl[i] && qq[i][hd[i]] > maxN){
             maxN = qq[i][hd[i]];
             dir = i;
         }
     )
         hd[dir]++;
     return maxN;
 }

 inline void insert(int dir , int num){
     qq[dir][tl[dir]++] = num;
 }

 inline bool cmp(int a , int b){
     return a > b;
 }

 int main(){
     cin >> n >> m >> q >> u >> v >> t;
      ; i < n ; i++)
         cin >> qq[][i];
     tl[] = n;
     sort(qq[] , qq[] + n , cmp);
      ; i <= m ; i++){
         ) * q;
         )
             cout << k << ' ';
         int x = (long long)k * u / v;
         insert( , x - i * q);
         insert( , k - x - i * q);
     }
     cout << endl;
     ;
     while(k != -inf){
         cnt++;
         )
             cout << k + m * q << ' ';
         k = top();
     }
     ;
 }

蚯蚓

 //状压DP
 #include<bits/stdc++.h>
 #define eps 1e-12
 using namespace std;
 inline int min(int a , int b){return a < b ? a : b;}
 ] , y[];
  << ] , N , pwx[] , numPWX;
 inline void init(){
      ; i < N ; i++){
         ;
          ; j < N ; j++){
             if(x[i] >= x[j] - eps && x[i] <= x[j] + eps)
                 continue;
             ;
              ; k <= numPWX && ff ; k++)
                  << i) | ( << j))) == (( << i) | ( << j)))
                     ff = ;
             if(!ff)
                 continue;
             double a = (y[i] * x[j] - x[i] * y[j]) / x[i] / x[j] / (x[i] - x[j]);
             if(a > -eps)
                 continue;
             double b = (y[i] - a * x[i] * x[i]) / x[i];
              << i) | ( << j);
              ; k < N ; k++)
                 if(a * x[k] * x[k] + b * x[k] >= y[k] - eps && a * x[k] * x[k] + b * x[k] <= y[k] + eps)
                     t |=  << k;
             pwx[++numPWX] = t;
             f = ;
         }
         if(!f){
             ;
              ; j <= numPWX && ff ; j++)
                  << i)) == ( << i))
                     ff = ;
             if(ff)
                 pwx[++numPWX] =  << i;
         }
     }
 }
 int main(){
     int T , m;
     for(scanf("%d" , &T) ; T ; T--){
         numPWX = ;
         minN[] = ;
         scanf("%d%d" , &N , &m);
         memset(minN ,  ,  << N));
         minN[] = ;
          ; i < N ; i++)
             scanf("%lf %lf" , x + i , y + i);
         init();
          ; i < ( << N) -  ; i++)
             if(minN[i] < N)
                  ; j <= numPWX ; j++)
                     minN[i | pwx[j]] = min(minN[i | pwx[j]] , minN[i] + );
         printf( << N) - ]);
     }
     ;
 }

*愤怒的小鸟

 //树上差分+线段树合并
 #include<bits/stdc++.h>
 #define mid ((l + r) >> 1)
 //This code is written by Itst
 using namespace std;

 inline int read(){
     ;
     ;
     char c = getchar();
     while(c != EOF && !isdigit(c)){
         if(c == '-')
             f = ;
         c = getchar();
     }
     while(c != EOF && isdigit(c)){
         a = (a << ) + (a << ) + (c ^ ');
         c = getchar();
     }
     return f ? -a : a;
 }

 ;
 struct Edge{
     int end , upEd;
 }Ed[MAXN * ];
 struct query{
     int from , to , val;
 }q1[MAXN] , q2[MAXN];
 struct node{
     int l , r , val;
 }Tree[MAXN * ];
 ] , root[MAXN] , times[MAXN] , ans[MAXN] , cntNode , N , M , cntEd;

 inline void addEd(int a , int b){
     Ed[++cntEd].end = b;
     Ed[cntEd].upEd = head[a];
     head[a] = cntEd;
 }

 inline void pushup(int now){
     Tree[now].val = Tree[Tree[now].l].val + Tree[Tree[now].r].val;
 }

 void insert(int& now , int l , int r , int tar , int val){
     if(!now){
         now = ++cntNode;
         Tree[now].l = Tree[now].r = Tree[now].val = ;
     }
     if(l == r){
         Tree[now].val += val;
         return;
     }
     if(mid >= tar)
         insert(Tree[now].l , l , mid , tar , val);
     else
         insert(Tree[now].r , mid +  , r , tar , val);
     pushup(now);
 }

 int query(int now , int l , int r , int tar){
     if(!Tree[now].val)
         ;
     if(l == r)
         return Tree[now].val;
     if(mid >= tar)
         return query(Tree[now].l , l , mid , tar);
      , r , tar);
 }

 int merge(int p , int q){
     if(!p)
         return q;
     if(!q)
         return p;
     Tree[p].val += Tree[q].val;
     Tree[p].l = merge(Tree[p].l , Tree[q].l);
     Tree[p].r = merge(Tree[p].r , Tree[q].r);
     return p;
 }

 void dfs(int now , int fa){
     dep[now] = dep[fa] + ;
     jump[now][] = fa;
      ; i <  ; i++)
         jump[now][i] = jump[jump[now][i - ]][i - ];
     for(int i = head[now] ; i ; i = Ed[i].upEd)
         if(Ed[i].end != fa)
             dfs(Ed[i].end , now);
 }

 int jumpToLCA(int x , int y){
     if(dep[x] < dep[y])
         swap(x , y);
      ; i >=  ; i--)
          << i) >= dep[y])
             x = jump[x][i];
     if(x == y)
         return x;
      ; i >=  ; i--)
         if(jump[x][i] != jump[y][i]){
             x = jump[x][i];
             y = jump[y][i];
         }
     ];
 }

 int jumpToCH(int x , int y){
      ; i >=  ; i--)
         if(jump[x][i] != y)
             x = jump[x][i];
     return x;
 }

 void Dfs(int now){
     for(int i = head[now] ; i ; i = Ed[i].upEd)
         ]){
             Dfs(Ed[i].end);
             root[now] = merge(root[now] , root[Ed[i].end]);
         }
     ans[now] += query(root[now] ,  , N <<  , times[now] + dep[now]);
 }

 void DFS(int now){
     for(int i = head[now] ; i ; i = Ed[i].upEd)
         ]){
             DFS(Ed[i].end);
             root[now] = merge(root[now] , root[Ed[i].end]);
         }
     ans[now] += query(root[now] , -N , N , times[now] - dep[now]);
 }

 int main(){
 #ifdef OJ
     freopen("1600.in" , "r" , stdin);
     //freopen("1600.out" , "w" , stdout);
 #endif
     N = read();
     M = read();
      ; i < N ; i++){
         int a = read() , b = read();
         addEd(a , b);
         addEd(b , a);
     }
      ; i <= N ; i++)
         times[i] = read();
     dfs( , );
      ; i <= M ; i++){
         int a = read() , b = read() , t = jumpToLCA(a , b);
         q1[i].from = a;
         q1[i].to = t;
         q1[i].val = dep[a];
         q2[i].from = b;
         q2[i].to = jump[t][];
         q2[i].val = dep[a] - (dep[t] << );
     }
      ; i <= M ; i++){
         insert(root[q1[i]. , N <<  , q1[i].val , );
         insert(root[q1[i].to] ,  , N <<  , q1[i].val , -);
     }
     Dfs();
     cntNode = ;
     memset(root ,  , sizeof(root));
      ; i <= M ; i++){
         insert(root[q2[i].);
         insert(root[q2[i].to] , -N , N , q2[i].val , -);
     }
     DFS();
      ; i <= N ; i++)
         printf("%d " , ans[i]);
     ;
 }

*天天爱跑步

NOIP2017(clear)

 //小学奥数结论题了解一下
 #include<bits/stdc++.h>
 using namespace std;
 int main()
 {
     unsigned long long a , b;
     cin >> a >> b;
     cout << a * b - a - b;
     ;
 }

小凯的疑惑

 //比较清爽的大模拟
 #include<bits/stdc++.h>
 //This code is written by Itst
 using namespace std;

 inline int read(){
     ;
     ;
     char c = getchar();
     while(c != EOF && !isdigit(c)){
         if(c == '-')
             f = ;
         c = getchar();
     }
     while(c != EOF && isdigit(c)){
         a = (a << ) + (a << ) + (c ^ ');
         c = getchar();
     }
     return f ? -a : a;
 }

 inline bool getF(){
     char c = getchar();
     while(!isupper(c))
         c = getchar();
     return c == 'F';
 }

 ];
 map < int , string > m;
 set < string > h;

 bool cmp(string l , string r){
     if(r == "n")
         ;
     if(l == "n" && r != "n")
         ;
     if(l.size() != r.size())
         return l.size() > r.size();
      ; i < l.size() ; i++)
         if(l[i] != r[i])
             return l[i] > r[i];
     ;
 }

 int main(){
 #ifdef LG
     freopen("3952.in" , "r" , stdin);
     //freopen("3952.out" , "w" , stdout);
 #endif
     for(int T = read() ; T ; --T){
         h.clear();
          , maxN =  , top =  , now = ;
         ;
         char c = getchar();
         ')
             c = getchar();
         if(c == 'n')
             pw = read();
          ; i <= L ; i++)
             if(getF()){
                 string s , l , r;
                 cin >> s >> l >> r;
                 if(h.count(s))
                     ifERR = ;
                 else{
                     h.insert(s);
                     m[top + ] = s;
                     if(cmp(l , r))
                         st[++top] = -;
                     else
                         if(r == "n" && l != "n")
                             st[++top] = ;
                         else
                             st[++top] = ;
                     now += st[top];
                     maxN = max(maxN , now);
                 }
             }
             else
                 if(!top)
                     ifERR = ;
                 else{
                     now -= st[top];
                     h.erase(m.find(top--)->second);
                 }
         if(top || ifERR)
             puts("ERR");
         else
             puts(pw == maxN ? "Yes" : "No");
     }
     ;
 }

时间复杂度

 //最短路+记搜
 #include<bits/stdc++.h>
 #define int long long
 #define MAXN 100010
 using namespace std;

 inline int read(){
     ;
     ;
     char c = getchar();
     while(!isdigit(c)){
         if(c == '-')
             f = ;
         c = getchar();
     }
     while(isdigit(c)){
         a = (a << ) + (a << ) + (c ^ ');
         c = getchar();
     }
     return f ? -a : a;
 }

 struct Edge{
     int end , upEd , w;
 }Ed[MAXN << ] , fanEd[MAXN << ];
 ] , minDis[MAXN] , fanHead[MAXN] , head[MAXN] , N , K , cntEd , cntFanEd , P;
 priority_queue < pair < int , int > > q;
 ];

 inline void addEd(int a , int b , int c){
     Ed[++cntEd].end = b;
     Ed[cntEd].upEd = head[a];
     Ed[cntEd].w = c;
     head[a] = cntEd;
 }

 inline void addFanEd(int a , int b , int c){
     fanEd[++cntFanEd].end = b;
     fanEd[cntFanEd].upEd = fanHead[a];
     fanEd[cntFanEd].w = c;
     fanHead[a] = cntFanEd;
 }

 int dfs(int now , int sub){
     if(sub > K)
         ;
     if(vis[now][sub])
         ;
     )
         return ans[now][sub];
     ans[now][sub] = ;
     vis[now][sub] = ;
     for(int i = head[now] ; i ; i = Ed[i].upEd){
         int t = dfs(Ed[i].end , minDis[Ed[i].end] + Ed[i].w - minDis[now] + sub);
         )
             ;
         else
             ans[now][sub] = (ans[now][sub] + t) % P;
     }
     vis[now][sub] = ;
     if(now == N)
         ans[now][sub]++;
     return ans[now][sub];
 }

 void Dijk(){
     memset(minDis , 0x3f , sizeof(minDis));
     minDis[N] = ;
     q.push(make_pair( , N));
     while(!q.empty()){
         pair < int , int > t = q.top();
         q.pop();
         if(-t.first > minDis[t.second])
             continue;
         for(int i = fanHead[t.second] ; i ; i = fanEd[i].upEd)
             if(minDis[fanEd[i].end] > minDis[t.second] + fanEd[i].w){
                 minDis[fanEd[i].end] = minDis[t.second] + fanEd[i].w;
                 q.push(make_pair(-minDis[fanEd[i].end] , fanEd[i].end));
             }
     }
 }

 main(){
     for(int T = read() ; T ; T--){
         N = read();
         int M = read();
         K = read();
         P = read();
         memset(fanHead ,  , sizeof(fanHead));
         memset(head ,  , sizeof(head));
         memset(ans , - , sizeof(ans));
         memset(vis ,  , sizeof(vis));
         cntEd = cntFanEd = ;
         while(M--){
             int a = read() , b = read() , c = read();
             addEd(a , b , c);
             addFanEd(b , a , c);
         }
         Dijk();
         cout << dfs( , ) << endl;
     }
     ;
 }

*逛公园

 //记忆化搜索
 #include<bits/stdc++.h>
 #define MAXN 1001
 #define dou double
 using namespace std;
 ] , v[MAXN] , T;
 dou mm[MAXN][MAXN];
 dou dis(dou x1 , dou x2 , dou y1 , dou y2 , dou z1 , dou z2)
 {
     return sqrt((x1 - x2) * (x1 - x2) +(y1 - y2) * (y1 - y2)  +(z1 - z2) * (z1 - z2));
 }
 bool sr(int m)
 {
     v[m] = ;
     ;
     ] + r >= h) o = ;
      ; i <= n && !o ; i++)
         if(i != m && !v[i])
             {
                 if(!mm[i][m])
                     mm[m][i] = dis(p[i][] , p[m][] , p[i][] , p[m][] , p[i][] , p[m][]);
                 else    continue;
                  * r)    o = sr(i);
             }
     return o;
 }
 int main()
 {
     ios::sync_with_stdio(false);
     ;
     for(cin >> T ; T ; T--)
     {
         cin >> n >> h >> r;
          ; i <= n ; i++)
         {
             cin >> p[i][] >> p[i][] >> p[i][];
             v[i] = ;
              ; j <= n ; j++)    mm[i][j] = ;
         }
         ;
          ; i <= n && !o ; i++)    ] - r <= ) o = sr(i);
         cout << (b ? "\n" : "") << (o ? "Yes" : "No");
         b = ;
     }
     ;
 }

奶酪

*宝藏

 //拆点Splay->动态开点线段树
 // luogu-judger-enable-o2
 #include<bits/stdc++.h>
 #define int long long
 using namespace std;

 inline int read(){
     ;
     char c = getchar();
     while(!isdigit(c))
         c = getchar();
     while(isdigit(c)){
         a = (a << ) + (a << ) + (c ^ ');
         c = getchar();
     }
     return a;
 }

 ;
 struct node{
     ];
 }Tree[];
 ] , rootBef[MAXN + ] , rootBeh[MAXN + ];

 inline int create(int l , int r , bool f){
     int t = ++cntNode;
     Tree[t].l = l;
     Tree[t].r = r;
     if(f)
         Tree[t].size = r - l + ;
     return t;
 }

 inline void split(int now , bool f){
     Tree[now].ch[] = create(Tree[now].l , Tree[now].r + Tree[now].l >>  , f);
     Tree[now].ch[] = create(Tree[now].l + Tree[now].r +  >>  , Tree[now].r , f);
 }

 int findKth(int now , int k , bool f){
     Tree[now].size--;
     if(Tree[now].l == Tree[now].r)
         return f ? Tree[now].val : Tree[now].l;
     ] && !Tree[now].ch[])
         split(now , );
     ]].size < k)
         ] , k - Tree[Tree[now].ch[]].size , f);
     ] , k , f);
 }

 void insert(int now , int tar , int k){
     Tree[now].size++;
     if(Tree[now].l == Tree[now].r){
         Tree[now].val = k;
         return;
     }
     ])
         split(now , );
     ]].r)
         insert(Tree[now].ch[] , tar , k);
     else
         insert(Tree[now].ch[] , tar , k);
 }

 signed main(){
     N = read();
     M = read();
     Q = read();
      ; i <= N ; i++){
         rootBef[i] = create( , M -  , );
         rootBeh[i] = create( , Q , );
     }
     rootBef[N + ] = create( , N , );
     rootBeh[N + ] = create( , Q , );
      ; i <= N ; i++)
         insert(rootBef[N + ] , i , i * M);
      ; i <= Q ; i++){
         int a = read() , b = read() , t;
         if(b == M)
             t = Tree[rootBef[N + ]].size >= a ? findKth(rootBef[N + ] , a , ) : findKth(rootBeh[N + ] , a - Tree[rootBef[N + ]].size , );
         else{
             t = Tree[rootBef[a]].size >= b ? findKth(rootBef[a] , b , ) + (a - ) * M : findKth(rootBeh[a] , b - Tree[rootBef[a]].size , );
             insert(rootBeh[a] , ++cnt[a] , Tree[rootBef[N + ]].size >= a ? findKth(rootBef[N + ] , a , ) : findKth(rootBeh[N + ] , a - Tree[rootBef[N + ]].size , ));
         }
         printf("%lld\n" , t);
         insert(rootBeh[N + ] , i , t);
     }
     ;
 }

*列队

NOIP2002-2017提高组题解的更多相关文章

  1. noip2010提高组题解

    NOIP2010提高组题解 T1:机器翻译 题目大意:顺序输入n个数,有一个队列容量为m,遇到未出现元素入队,求入队次数. AC做法:直接开1000的队列模拟过程. T2:乌龟棋 题目大意:有长度为n ...

  2. NOIP 2014 提高组 题解

    NOIP 2014 提高组 题解 No 1. 生活大爆炸版石头剪刀布 http://www.luogu.org/problem/show?pid=1328 这是道大水题,我都在想怎么会有人错了,没算法 ...

  3. NOIP 2001 提高组 题解

    NOIP 2001 提高组 题解 No 1. 一元三次方程求解 https://vijos.org/p/1116 看见有人认真推导了求解公式,然后猥琐暴力过的同学们在一边偷笑~~~ 数据小 暴力枚举即 ...

  4. NOIP 2000 提高组 题解

    NOIP2000 提高组 题解 No 1. 进制转换 https://www.rqnoj.cn/problem/295 水题 对于n和基数r, 每次用n mod r, 把余数按照逆序排列 注意 mod ...

  5. 【NOIP2018】提高组题解

    [NOIP2018]提高组题解 其实就是把写过的打个包而已 道路铺设 货币系统 赛道修建 旅行 咕咕咕 咕咕咕

  6. NOIP 2017 提高组 day1t2 时间复杂度

    P3952 时间复杂度 标签 NOIp提高组 2017 时空限制 1000ms / 128MB 小明正在学习一种新的编程语言 A++,刚学会循环语句的他激动地写了好多程序并 给出了他自己算出的时间复杂 ...

  7. noip2002提高组题解

    再次280滚粗.今天早上有点事情,所以做题的时候一直心不在焉,应该是三天以来状态最差的一次,所以这个分数也还算满意了.状态真的太重要了. 第一题:均分纸牌 贪心.(昨天看BYVoid的noip2001 ...

  8. noip2009提高组题解

    NOIP2009题解 T1:潜伏者 题目大意:给出一段密文和破译后的明文,一个字母对应一个密文字母,要求破译一段密文,如果有矛盾或有未出现密文无法破译输出failed,否则输出明文. 思路:纯模拟题 ...

  9. noip2008提高组题解

    第一题:笨小猴 模拟   第二题:火柴棒等式 搜索 深搜不用说,确定出两个加数然后判断能否拼出等式. 枚举确实不太好搞,因为枚举范围不确定,太大了容易超时,太小了容易漏解.不过这题的数据貌似很温和,我 ...

  10. noip2007提高组题解

    题外话:这一年的noip应该是最受大众关心的,以至于在百度上输入noip第三个关键字就是noip2007.主要是由于这篇文章:http://www.zhihu.com/question/2110727 ...

随机推荐

  1. MySQL数据库导入错误:ERROR 1064 (42000) 和 ERROR at line xx: Unknown command '\Z'.

    使用mysqldump命令导出数据: D:\Program Files\MySQL\MySQL Server 5.6\bin>mysqldump -hlocalhost -uroot -proo ...

  2. .Net Core(三)MVC Core

    MVC Core的改动感觉挺大的,需要的功能大多从Nuget安装,还内置了IOC,支持SelfHost方式运行等等. 一.项目结构的变化创建的新MVC项目的结构发生了变化,比如:静态文件需要统一放置到 ...

  3. unicode编码和utf8编码的区别

    编码格式不同在数据的传输和显示会有很大的影响.最近在使用的过程中发现一些网络文件 传输的编码格式问题,会影响文件的正常传输,于是查看了一下网上的资料,自己也写一篇 小总结. uicode是万国码,用1 ...

  4. Modo教程合集44部

    Modo教程合集44部 教程说明:英文视频教程,大部分有工程文件,但不是全部 教程格式:Flv.MP4格式,大部分高清,确保能看清软件上的文字 发货方式:百度网盘下载链接(教程较多,可转存到自己的网盘 ...

  5. Android视屏播放兼容性问题分享

    最近产品提了一个紧急需求:webview加载的URL,需要支持视频播放. 为了快速完成需求,功能实现上直接使用系统自带播放器播放视频.由于是自带播放器,需要进行兼容性测试,过程发现了不少问题,这里分享 ...

  6. Spark线性回归实现优化

    import org.apache.log4j.{Level, Logger} import org.apache.spark.ml.feature.VectorAssembler import or ...

  7. 洗礼灵魂,修炼python(43)--巩固篇—经典类/新式类

    经典类 1.什么是经典类 就是在使用class关键词时,括号内不添加object类的就叫经典类,前面的博文里是绝对解析过的,所以你应该知道,经典类现在已经仅存在于python2了,因为python3不 ...

  8. CPUFreq驱动

    CPUFreq子系统位于 drivers/cpufreq目录下,负责进行运行过程中CPU频率和电压的动态调整,即DvFS( Dynamic Voltage Frequency Scaling,动态电压 ...

  9. Jenkins修改workspace和build目录

    Jenkins: Change Workspaces and Build Directory Locations  转自: http://ingorichter.blogspot.jp/2012/02 ...

  10. 【PAT】B1063 计算谱半径(20 分)

    水题,没有难点 #include<stdio.h> #include<algorithm> #include<math.h> using namespace std ...