You can not select more than 25 topics Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.

47 lines
1.8 KiB

2 years ago
#include <bits/stdc++.h>
using namespace std;
const int N = 110, M = 10, INF = 0x3f3f3f3f;
int n, m;
int w[N], s[N];
int f[N][N][M], g[N][N][M];
int get_mod(int x) {
return (x % 10 + 10) % 10;
}
int main() {
cin >> n >> m;
for (int i = 1; i <= n; i++) {
cin >> w[i];
w[i + n] = w[i]; // 破环成链
}
for (int i = 1; i <= n * 2; i++) s[i] = s[i - 1] + w[i]; // 预处理前缀和,下标从1开始
memset(f, 0x3f, sizeof f); // 预求最小,先设最大
memset(g, -0x3f, sizeof g); // 预求最大,先设最小
for (int len = 1; len <= n; len++) // 区间DP,先枚举长度
for (int l = 1; l + len - 1 <= n * 2; l++) { // 枚举起点
int r = l + len - 1; // 计算终点
// DP 初始化
// 边界条件是全部划分为k=1,也就是一块时的结果是多少根据题意一整块当然就是区间内容相加后对10取模
f[l][r][1] = g[l][r][1] = get_mod(s[r] - s[l - 1]);
// 状态转移
for (int k = 2; k <= m; k++) // 枚举每个可以划分成的部分
for (int j = l + k - 2; j <= r - 1; j++) { // 枚举K-1部分时的最后一个终点位置
f[l][r][k] = min(f[l][r][k], f[l][j][k - 1] * get_mod(s[r] - s[j]));
g[l][r][k] = max(g[l][r][k], g[l][j][k - 1] * get_mod(s[r] - s[j]));
}
}
// 枚举每个区间长度为n的区间获取符合长度要求的区间内划分成m块的最大、最小值
int mx = -INF, mi = INF;
for (int i = 1; i <= n; i++) {
mx = max(mx, g[i][i + n - 1][m]);
mi = min(mi, f[i][i + n - 1][m]);
}
cout << mi << endl;
cout << mx << endl;
return 0;
}