Yahoo Programming Contest 2019 D - Ears

D - Ears

思路:

s:起点           t:终点           l:左端点           r:右端点

以上称为关键点

dp[i][j]表示到位置 i 为止,已经经过前 j 个关键点的最小花费

转移方程看代码:

#pragma GCC optimize(2)
#pragma GCC optimize(3)
#pragma GCC optimize(4)
#include<bits/stdc++.h>
using namespace std;
#define y1 y11
#define fi first
#define se second
#define pi acos(-1.0)
#define LL long long
//#define mp make_pair
#define pb push_back
#define ls rt<<1, l, m
#define rs rt<<1|1, m+1, r
#define ULL unsigned LL
#define pll pair<LL, LL>
#define pli pair<LL, int>
#define pii pair<int, int>
#define piii pair<pii, int>
#define pdd pair<double, double>
#define mem(a, b) memset(a, b, sizeof(a))
#define debug(x) cerr << #x << " = " << x << "\n";
#define fio ios::sync_with_stdio(false);cin.tie(0);cout.tie(0);
//head

const int N = 2e5 + 10;
LL dp[N][5]; 
int a[N];
int main() {
    int n;
    scanf("%d", &n);
    for (int i = 1; i <= n; ++i) scanf("%d", &a[i]);    
    for (int i = 1; i <= n; i++) {
        dp[i][0] = dp[i-1][0] + a[i];
        for (int j = 1; j < 5; j++) {
            dp[i][j] = dp[i-1][j];
            for (int k = 0; k < j; k++) dp[i][j] = min(dp[i][j], dp[i-1][k]);
        }
        dp[i][1] += a[i] == 0 ? 2 : (a[i]%2 != 0);
        dp[i][2] += a[i]%2 != 1;
        dp[i][3] += a[i] == 0 ? 2 : (a[i]%2 != 0);
        dp[i][4] += a[i];        
    }
    LL ans = dp[n][0];
    for (int i = 1; i < 5; i++) ans = min(ans, dp[n][i]);
    printf("%lld\n", ans);
    return 0;
}

猜你喜欢

转载自www.cnblogs.com/widsom/p/10359968.html