946D. Timetable

Posted xFANx

tags:

篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了946D. Timetable相关的知识,希望对你有一定的参考价值。

传送门

预处理加分组背包

 

n行m列,每列的花费是第一个与最后一个1的构成的区间长度,已知可以去除不多于k个1,求最小花费

 

#include <map>
#include <cstdio>
#include <cstring>
#include <algorithm>
#define INF 0x3f3f3f3f
using namespace std;
const int maxn = 1e6 + 10;
int n, m, k;

int A[510];
int cst[510][510];
int dp[510][510];

int main() {
    memset(cst, INF, sizeof(cst));
    memset(dp, INF, sizeof(dp));
    scanf("%d%d%d", &n, &m, &k);
    for (int i = 1; i <= n; i++) {
        A[0] = 0;
        int tmp;
        for (int j = 1; j <= m; j++) {
            scanf("%1d", &tmp);
            if (tmp == 1) {
                A[++A[0]] = j;
            }
        }
        cst[i][0] = A[0] == 0 ? 0 : A[A[0]] - A[1] + 1;
        for (int j = 1; j < A[0]; j++) {
            for (int kk = 1; kk <= j + 1; kk++) {
                cst[i][j] = min(cst[i][j], A[A[0] - (j - kk + 1)] - A[kk] + 1);
            }
        }
        for (int j = A[0]; j <= k; j++) cst[i][j] = 0;
    }
    dp[0][0] = 0;
    for (int i = 1; i <= n; i++) {
        for (int j = 0; j <= k; j++) {
            for (int kk = 0; kk <= j; kk++) {
                dp[i][j] = min(dp[i][j], dp[i - 1][j - kk] + cst[i][kk]);
            }                
        }
    }
    printf("%d\n", dp[n][k]);
    return 0;
}

 

以上是关于946D. Timetable的主要内容,如果未能解决你的问题,请参考以下文章

CodeForces 946D Timetable

CF946D Timetable 动态规划

Timetable CodeForces - 946D (区间dp)

Timetable CodeForces - 946D (预处理+背包)

#分组背包 Educational Codeforces Round 39 (Rated for Div. 2) D. Timetable

CF1204A BowWow and the Timetable