Hướng dẫn giải của duong3982oj Contest 01 - Dãy hình nón
Chỉ dùng lời giải này khi không có ý tưởng, và đừng copy-paste code từ lời giải này. Hãy tôn trọng người ra đề và người viết lời giải.
Nộp một lời giải chính thức trước khi tự giải là một hành động có thể bị ban.
Nộp một lời giải chính thức trước khi tự giải là một hành động có thể bị ban.
Subtask 1:
- Duyệt tất cả các hoán vị của mảng
để tìm xem số lần chia đoạn ít nhất thỏa mãn đề bài.
Độ phức tạp:
Subtask 2:
Ta có thể duyệt vét cạn khéo léo hơn, hoặc sử dụng DP bitmask.
Độ phức tạp:
Subtask 3 + Subtask 4:
Nhận xét: Ta sẽ chỉ cắt đoạn ở vị trí
Giả sử một đoạn
Đầu tiên, ta sẽ nén số mảng
-> Với cách tiếp cận này, đáp số bài toán chính là min(
Vậy, với mọi
Copy
int dp (int mid, int l, int r){
if (mid == -1) return L[l] + R[r - 1];
if (f[mid][l][r] != -1) return f[mid][l][r];
int val = (s[l] == mid);
if (l && s[l - 1] == mid){
l--; val++;
}
if (r < n && s[r] == mid && l != r){
val++; r++;
}
if (pos[mid].size () == val) return dp (mid - 1, l, r);
int b = 0;
if (s[l] != mid) b += L[l];
if (s[r - 1] != mid) b += R[r - 1];
int ret = n;
for (int i : pos[mid]){
if (i == l || i == r - 1) continue;
ret = min ({ret, dp (mid - 1, i, r) - L[i] - R[r - 1], dp (mid - 1, l, i + 1) - L[l] - R[i]});
for (int j : pos[mid]){
if (j != l && j + 1 != r && j != i) ret = min (ret, dp (mid - 1, i, j + 1) - L[i] - R[j]);
}
}
return f[mid][l][r] = ret + b + base[mid];
}
với
Độ phức tạp:
Bình luận