zoukankan      html  css  js  c++  java
  • Codeforces Round #466 (Div. 2) E. Cashback

    E. Cashback
    time limit per test
    2 seconds
    memory limit per test
    256 megabytes
    input
    standard input
    output
    standard output

    Since you are the best Wraith King, Nizhniy Magazin «Mir» at the centre of Vinnytsia is offering you a discount.

    You are given an array a of length n and an integer c.

    The value of some array b of length k is the sum of its elements except for the  smallest. For example, the value of the array [3, 1, 6, 5, 2] with c = 2 is 3 + 6 + 5 = 14.

    Among all possible partitions of a into contiguous subarrays output the smallest possible sum of the values of these subarrays.

    Input

    The first line contains integers n and c (1 ≤ n, c ≤ 100 000).

    The second line contains n integers ai (1 ≤ ai ≤ 109) — elements of a.

    Output

    Output a single integer  — the smallest possible sum of values of these subarrays of some partition of a.

    Examples
    input
    Copy
    3 5
    1 2 3
    output
    6
    input
    Copy
    12 10
    1 1 10 10 10 10 10 10 9 10 10 10
    output
    92
    input
    Copy
    7 2
    2 3 6 4 5 7 1
    output
    17
    input
    Copy
    8 4
    1 3 4 5 5 3 4 1
    output
    23
    Note

    In the first example any partition yields 6 as the sum.

    In the second example one of the optimal partitions is [1, 1], [10, 10, 10, 10, 10, 10, 9, 10, 10, 10] with the values 2 and 90 respectively.

    In the third example one of the optimal partitions is [2, 3], [6, 4, 5, 7], [1] with the values 3, 13 and 1 respectively.

    In the fourth example one of the optimal partitions is [1], [3, 4, 5, 5, 3, 4], [1] with the values 1, 21 and 1 respectively.

    思路:

            首先可以证明出最优方案中一定存在所有划分的块的元素量都不大于c。假设最优方案中存在大于c的块,规模为d,d % c = k, d / c = m, k不为0时,额外加入的这k个元素并不会使得当前块被砍掉的元素数量增多,也不会使被砍掉的元素增大,因此把这k个元素独立出来不会使结果变差;当k等于0时,即d是c的m倍时,合并m个规模为c的块不会使总共被砍掉的m个元素便大,相反可能变小。

            因此,我们考虑dp,dp[i]表示前i个元素可以被砍掉的最大和,则只需讨论目前最后一个(即第i个)元素是否被取到即可,被取到时,dp[i] = dp[i - c] + min(a[i - c + 1...i]);没被取到时,dp[i] = dp[i - 1]。其中求最小值可以用线段树维护。复杂度O(nlog(n))。

     1 #include <iostream>
     2 #include <fstream>
     3 #include <sstream>
     4 #include <cstdlib>
     5 #include <cstdio>
     6 #include <cmath>
     7 #include <string>
     8 #include <cstring>
     9 #include <algorithm>
    10 #include <queue>
    11 #include <stack>
    12 #include <vector>
    13 #include <set>
    14 #include <map>
    15 #include <list>
    16 #include <iomanip>
    17 #include <cctype>
    18 #include <cassert>
    19 #include <bitset>
    20 #include <ctime>
    21 
    22 using namespace std;
    23 
    24 #define pau system("pause")
    25 #define ll long long
    26 #define pii pair<int, int>
    27 #define pb push_back
    28 #define mp make_pair
    29 #define clr(a, x) memset(a, x, sizeof(a))
    30 
    31 const double pi = acos(-1.0);
    32 const int INF = 0x3f3f3f3f;
    33 const int MOD = 1e9 + 7;
    34 const double EPS = 1e-9;
    35 
    36 /*
    37 #include <ext/pb_ds/assoc_container.hpp>
    38 #include <ext/pb_ds/tree_policy.hpp>
    39 
    40 using namespace __gnu_pbds;
    41 tree<pli, null_type, greater<pli>, rb_tree_tag, tree_order_statistics_node_update> T;
    42 */
    43 
    44 int mi[400015], n, c;
    45 ll sum;
    46 void pushup(int i) {
    47     mi[i] = min(mi[i << 1], mi[i << 1 | 1]);
    48 }
    49 void build(int i, int l, int r) {
    50     if (l == r) {
    51         scanf("%d", &mi[i]);
    52         sum += mi[i];
    53         return;
    54     }
    55     int mi = l + r >> 1;
    56     build(i << 1, l, mi);
    57     build(i << 1 | 1, mi + 1, r);
    58     pushup(i);
    59 }
    60 int query(int i, int l, int r, int x, int y) {
    61     if (x <= l && r <= y) {
    62         return mi[i];
    63     }
    64     int mi = l + r >> 1;
    65     int res1 = MOD, res2 = MOD;
    66     if (x <= mi) res1 = query(i << 1, l, mi, x, y);
    67     if (mi < y) res2 = query(i << 1 | 1, mi + 1, r, x, y);
    68     return min(res1, res2);
    69 }
    70 ll dp[100015];
    71 int main() {
    72     scanf("%d%d", &n, &c);
    73     build(1, 1, n);
    74     for (int i = c; i <= n; ++i) {
    75         int res = query(1, 1, n, i - c + 1, i);
    76         dp[i] = max(dp[i - 1], dp[i - c] + res);
    77     }
    78     printf("%lld", sum - dp[n]);
    79     return 0;
    80 }
  • 相关阅读:
    ps -aux --sort -rss |head 列出进程拿物理内存占用排序 使用ps aux 查看系统进程时,第六列即 RSS列显示的就是进程使用的物理内存。
    13 memcache服务检查
    shell 颜色
    expr判断整数是相加的值,返回命令的返回值$? 是0,但是少数情况是1,例如1 + -1 ,$? 的结果是1 ,判断要大于1最准确
    ZABBIX监控原理
    ansible分发密钥
    再来一个expect脚本
    11:菜单自动化软件部署经典案例
    19:批量检查多个网站地址是否正常
    数组迭代
  • 原文地址:https://www.cnblogs.com/BIGTOM/p/8468147.html
Copyright © 2011-2022 走看看