比赛 |
2025暑期集训第6场 |
评测结果 |
C |
题目名称 |
Moortal Cowmbat |
最终得分 |
0 |
用户昵称 |
健康铀 |
运行时间 |
0.000 s |
代码语言 |
C++ |
内存使用 |
0.00 MiB |
提交时间 |
2025-07-12 11:45:49 |
显示代码纯文本
#include <bits/stdc++.h>
using namespace std;
const int INF = 1e9;
class SegTree {
public:
int n;
vector<int> t;
SegTree(int size) {
n = size;
t.resize(4 * n, INF);
}
void upd(int idx, int val, int v = 0, int l = 0, int r = -1) {
if (r == -1) r = n - 1;
if (l == r) {
t[v] = val;
return;
}
int m = (l + r) / 2;
if (idx <= m) upd(idx, val, 2 * v + 1, l, m);
else upd(idx, val, 2 * v + 2, m + 1, r);
t[v] = min(t[2 * v + 1], t[2 * v + 2]);
}
int qry(int ql, int qr, int v = 0, int l = 0, int r = -1) {
if (r == -1) r = n - 1;
if (ql > qr) return INF;
if (ql <= l && r <= qr) return t[v];
int m = (l + r) / 2;
int res = INF;
if (ql <= m) res = min(res, qry(ql, qr, 2 * v + 1, l, m));
if (qr > m) res = min(res, qry(ql, qr, 2 * v + 2, m + 1, r));
return res;
}
};
int main() {
freopen("cowmbat.in","r",stdin);
freopen("cowmbat.out","w",stdout);
int N, M, K;
fin >> N >> M >> K;
string S;
fin >> S;
vector<vector<int>> a(M, vector<int>(M));
for (int i = 0; i < M; i++) {
for (int j = 0; j < M; j++) {
fin >> a[i][j];
}
}
vector<vector<int>> dist = a;
for (int k = 0; k < M; k++) {
for (int i = 0; i < M; i++) {
for (int j = 0; j < M; j++) {
if (dist[i][k] + dist[k][j] < dist[i][j]) {
dist[i][j] = dist[i][k] + dist[k][j];
}
}
}
}
vector<SegTree> st(M);
for (int i = 0; i < M; i++) {
st[i] = SegTree(N + 1);
st[i].upd(0, 0);
}
vector<int> dp(N + 1, INF);
dp[0] = 0;
vector<vector<int>> pref(N + 1, vector<int>(M, 0));
for (int i = 1; i <= N; i++) {
int c0 = S[i - 1] - 'a';
for (int c = 0; c < M; c++) {
pref[i][c] = pref[i - 1][c] + dist[c0][c];
}
if (i >= K) {
dp[i] = INF;
for (int c = 0; c < M; c++) {
int mn = st[c].qry(0, i - K);
if (mn < INF) {
dp[i] = min(dp[i], mn + pref[i][c]);
}
}
if (dp[i] < INF) {
for (int c = 0; c < M; c++) {
st[c].upd(i, dp[i] - pref[i][c]);
}
}
}
}
fout << dp[N] << endl;
fin.close();
fout.close();
return 0;
}