zoukankan      html  css  js  c++  java
  • Codeforces Round #523 (Div. 2) Solution

    A. Coins

    Water.

     1 #include <bits/stdc++.h>
     2 using namespace std;
     3 int n, s;
     4 
     5 int main()
     6 {
     7     while (scanf("%d%d", &n, &s) != EOF)
     8     {
     9         int res = 0;
    10         for (int i = n; i >= 1; --i) while (s >= i) 
    11         {
    12             ++res;
    13             s -= i;
    14         }
    15         printf("%d
    ", res);
    16     }
    17     return 0;
    18 }
    View Code

    B. Views Matter

    Solved.

    题意:

    有n个栈,不受重力影响,在保持俯视图以及侧视图不变的情况下,最多可以移掉多少个方块

    思路:

    考虑原来那一列有的话那么这一列至少有一个,然后贪心往高了放

     1 #include <bits/stdc++.h>
     2 using namespace std;
     3 
     4 #define ll long long
     5 #define N 100010
     6 int n, m;
     7 ll a[N], sum;
     8 
     9 int main()
    10 {
    11     while (scanf("%d%d", &n, &m) != EOF)
    12     {
    13         sum = 0;
    14         for (int i = 1; i <= n; ++i) scanf("%lld", a + i), sum += a[i];
    15         sort(a + 1, a + 1 + n);
    16         ll res = 0, high = 0;
    17         for (int i = 1; i <= n; ++i) if (a[i] > high) 
    18             ++high;
    19         printf("%lld
    ", sum - n - a[n] + high);
    20     }
    21     return 0;
    22 }
    View Code

    C. Multiplicity

    Upsolved.

    题意:

    定义一个序列为好的序列即$b_1, b_2, ...., b_k 中i in [1, k] 使得 b_i % i == 0$

    求有多少个好的子序列

    思路:

    考虑$Dp$

    $令dp[i][j] 表示第i个数,长度为j的序列有多少种方式$

    $dp[i][j] = dp[i - 1][j - 1] + dp[i - 1][j]   (arr[j] % j == 0)$

    否则 $dp[i][j] = dp[i - 1][j]$

    然后不能暴力递推,只需要更新$arr[j] % j == 0 的j即可$

     1 #include <bits/stdc++.h>
     2 using namespace std;
     3 
     4 #define ll long long
     5 #define N 1000100
     6 const ll MOD = (ll)1e9 + 7;
     7 int n; ll a[N], dp[N];
     8 
     9 int main()
    10 {
    11     while (scanf("%d", &n) != EOF)
    12     {
    13         for (int i = 1; i <= n; ++i) scanf("%lld", a + i);
    14         memset(dp, 0, sizeof dp);
    15         dp[0] = 1;    
    16         for (int i = 1; i <= n; ++i)
    17         {
    18             vector <int> cur;
    19             for (int j = 1; j * j <= a[i]; ++j)
    20             {
    21                 if (a[i] % j == 0)
    22                 {
    23                     cur.push_back(j);
    24                     if (j != a[i] / j)
    25                         cur.push_back(a[i] / j);
    26                 }
    27             }
    28             sort(cur.begin(), cur.end());
    29             reverse(cur.begin(), cur.end());
    30             for (auto it : cur)
    31                 dp[it] = (dp[it] + dp[it - 1]) % MOD;
    32         }
    33         ll res = 0;
    34         for (int i = 1; i <= 1000000; ++i) res = (res + dp[i]) % MOD;
    35         printf("%lld
    ", res);    
    36     }
    37     return 0;
    38 }
    View Code

    D. TV Shows

    Upsolved.

    题意:

    有n个电视节目,每个节目播放的时间是$[l, r],租用一台电视机的费用为x + y cdot time$

    一台电视机同时只能看一个电视节目,求看完所有电视节目最少花费

    思路:

    贪心。

    因为租用电视机的初始费用是相同的,那么我们将电视节目将左端点排序后

    每次选择已经租用的电视机中上次放映时间离自己最近的,还要比较租用新电视机的费用,

    如果是刚开始或者没有一台电视机闲着,则需要租用新的电视机

     1 #include <bits/stdc++.h>
     2 using namespace std;
     3 
     4 #define ll long long
     5 #define N 100010
     6 struct node
     7 {
     8     ll l, r;
     9     void scan() { scanf("%lld%lld", &l, &r); }
    10     bool operator < (const node &r) const 
    11     {
    12         return l < r.l || (l == r.l && this->r < r.r);
    13     }
    14 }arr[N];
    15 int n; ll x, y;
    16 const ll MOD = (ll)1e9 + 7;
    17 multiset <ll> se;
    18 
    19 int main()
    20 {
    21     while (scanf("%d%lld%lld", &n, &x, &y) != EOF) 
    22     {
    23         for (int i = 1; i <= n; ++i) arr[i].scan();
    24         sort(arr + 1, arr + 1 + n);
    25         ll res = 0;
    26         for (int i = 1; i <= n; ++i)
    27         {
    28             if (se.lower_bound(arr[i].l) == se.begin())
    29                 res = (res + x + y * (arr[i].r - arr[i].l) % MOD) % MOD;
    30             else
    31             {
    32                 int pos = *(--se.lower_bound(arr[i].l)); 
    33                 if (x < y * (arr[i].l - pos)) 
    34                     res = (res + x + y * (arr[i].r - arr[i].l) % MOD) % MOD;
    35                 else
    36                 {
    37                     se.erase(--se.lower_bound(arr[i].l));
    38                     res = (res + y * (arr[i].r - pos) % MOD) % MOD; 
    39                 }    
    40             }
    41             se.insert(arr[i].r); 
    42         }
    43         printf("%lld
    ", res);
    44     }
    45     return 0;
    46 }
    View Code

    E. Politics

    Unsolved.

    F. Lost Root

    Unsolved.

  • 相关阅读:
    [题解] uva 247 Calling Circles (floyd判联通/tarjan强连通分量)
    [总结] 最小生成树 minimum spanning tree
    [题解] uva 11865 Stream My Contest (二分+最小树形图)
    [题解] poj 3164 Command Network (朱刘算法 最小树形图(有向生成树))
    [题解] poj 3241 Object Clustering (kruskal曼哈顿距离最小生成树+树状数组)
    [BZOJ2301][HAOI2011]Problem b 莫比乌斯反演+容斥
    [BZOJ1101][POI2007]Zap 莫比乌斯反演
    [BZOJ4006][JLOI2015]管道连接 状压dp+斯坦纳树
    [BZOJ1494][NOI2007]生成树计数 状压dp 并查集
    [BZOJ1076][SCOI2008]奖励关 状压dp
  • 原文地址:https://www.cnblogs.com/Dup4/p/10034173.html
Copyright © 2011-2022 走看看