zoukankan      html  css  js  c++  java
  • CodeForces Round #585 (Div 2)

    score:1336 (-45), pupil
    Rank: 3313(又炸了,没啥好说的。。)

    B.http://codeforces.com/contest/1215/problem/B

    这个题万万没想到是dp,我的天,一开始直接上暴力,没仔细分析时间复杂度,估计是最近网络赛暴力惯了,没缓过神来。。。

    分析见代码:

     1 /*
     2     设pos[i]表示以i为结尾的正区间,neg[i]表示以i为结尾的负区间。状态转移很容易了,见代码
     3     这次真的wa到自闭了,后来改了改竟然又tle,真的自闭到家。。。自闭到家。。。。。
     4 */
     5 #include <bits/stdc++.h>
     6 using namespace std;
     7 typedef long long ll;
     8 const int maxn = 1e6;
     9 ll pos[maxn], neg[maxn];
    10 
    11 int main()
    12 {
    13     int n; cin >> n;
    14     int x;
    15     ll maxpos, maxneg;
    16 
    17     maxpos = maxneg = 0;
    18     for (int i = 1; i <= n; i++)
    19     {
    20         scanf("%d", &x);
    21         if (x < 0)
    22         {
    23             pos[i] = neg[i - 1];
    24             neg[i] = 1 + pos[i - 1];
    25         }
    26         else
    27         {
    28             pos[i] = 1 + pos[i - 1];
    29             neg[i] = neg[i - 1];
    30         }
    31         maxpos += pos[i];
    32         maxneg += neg[i];
    33     }
    34     cout << maxneg << " " << maxpos << endl;
    35 }

    C.http://codeforces.com/contest/1215/problem/C

    这道题也是,贪心想到了(而且很好想),但是情况没处理好,当ab和ba的情况加起来是奇数的时候输出-1,不然一定有解;

    当时以为ab和ba都为奇数的时候还需要一个aa或者bb来做媒介,但其实不用,ab可以自己交换,然后再跟ba交换,花费两次。

    代码如下:

     1 #include <bits/stdc++.h>
     2 using namespace std;
     3 const int maxn = 1e6;
     4 
     5 int vis[maxn];
     6 char a[maxn], b[maxn];
     7 
     8 int main()
     9 {
    10     int n; cin >> n;
    11     int same, ab, ba;
    12     vector<int> resa, resb;
    13 
    14     same = ab = ba = 0;
    15     scanf("%s%s", a + 1, b + 1);
    16     for (int i = 1; i <= n; i++)
    17     {
    18         vis[i] = a[i] == b[i] ? 1 : a[i] == 'a' ? 2 : 3;
    19         if (vis[i] == 1)
    20             continue;
    21         else if (vis[i] == 2)
    22             resa.push_back(i);
    23         else resb.push_back(i);
    24     }
    25     if ((resa.size() + resb.size()) & 1) return cout << -1 << endl, 0;
    26     printf("%d
    ", resa.size() / 2 + resb.size() / 2 + (resa.size() % 2 ? 2 : 0));
    27     for (int i = 1; i < resa.size(); i += 2)
    28         printf("%d %d
    ", resa[i - 1], resa[i]);
    29     for (int i = 1; i < resb.size(); i += 2)
    30         printf("%d %d
    ", resb[i - 1], resb[i]);
    31     if (resa.size() % 2)
    32     {
    33         printf("%d %d
    ", resa[resa.size() - 1], resa[resa.size() - 1]);
    34         printf("%d %d
    ", resb[resb.size() - 1], resa[resa.size() - 1]);
    35     }
    36 }

     D.http://codeforces.com/contest/1215/problem/D

    博弈论的题,博弈论做的比较少,但是基本都是分类讨论。这个题设两边的和sum1, sum2; 问号的和num1, num2;

    ①如果num1 == num2 && sum1 == sum2, B只需要每次在对面填充A的数就能赢;如果sum1 != sum2,A可以通过不断地在sum大的一方填充9就能赢

    ②如果num1 > num2

      如果sum1 == sum2, A通过不断在num1填9就能赢。

      如果sum1 > sum2, A通过不断在num1填9就能赢。

      如果sum1 < sum2, A一定先把sum1用9填完,同时B也用9在对面填(防止差距更大),最后只要sum2留下的?数目是2的整数倍并且两个sum的差是9的整数倍,而且倍数相同B就能赢,不然B一定输。

    这道题是后来补的,当时没做。。。  

    E.状压dp

    分析:dp[i]表示状态i时所需要移动的最小的次数。dp[i]一定是由当前状态在加上一个数字(1-20)得来。

    代码:

     1 #include <bits/stdc++.h>
     2 using namespace std;
     3 typedef long long ll;
     4 const ll inf = 0x3f3f3f3f3f3f3f3f;
     5 const int maxn = 1e6;
     6 ll cnt[21];
     7 ll f[21][21];
     8 ll dp[(1 << 20) + 10];
     9 
    10 int main()
    11 {
    12     int n; cin >> n;
    13     for (int i = 1; i <= n; i++)
    14     {
    15         int x; scanf("%d", &x);
    16         for (int i = 1; i <= 20; i++)
    17             f[x][i] += cnt[i];
    18         cnt[x]++;
    19     }
    20     memset(dp, inf, sizeof(dp));
    21     dp[0] = 0;
    22     for (int i = 1; i < (1 << 20); i++)
    23     {
    24         for(int j = 0; j < 20; j++)
    25             if (i & (1 << j))
    26             {
    27                 int last = i ^ (1 << j);
    28                 ll res = 0;
    29                 for(int k = 0; k < 20; k++)
    30                     if ((1 << k) & last)
    31                         res += f[j + 1][k + 1];
    32                 dp[i] = min(dp[i], dp[last] + res);
    33             }
    34     }
    35     cout << dp[(1 << 20) - 1] << endl;
    36 }

    代码:

  • 相关阅读:
    域渗透[WinRM]
    域渗透[DCSync]利用
    LLMNR中间人及WPAD劫持
    274. H-Index
    75. Sort Colors
    46. Permutations
    31. Next Permutation
    subsets
    86. Partition List
    82. Remove Duplicates from Sorted List II
  • 原文地址:https://www.cnblogs.com/liuwenhan/p/11526711.html
Copyright © 2011-2022 走看看