Search for a command to run...
Progressive hints first, then the full explanation and implementation when you're ready to cash out.
Review status
AI-generated and still unreviewed. Double-check the details before internalizing them.
Hints
Open only as much as you need to keep the solve alive.
A pair of consecutive values is bad exactly when the two values are equal or opposite. Since opposite faces are and , bad means or .
Changing one element only affects the two edges touching it: and . So one operation can never repair more than two adjacent bad pairs.
If you meet a bad pair , you can always change to fix both and at once, if exists.
Why is that always possible? The new value for only has to avoid , , , and . That forbids at most of the faces.
So scan left to right. Whenever the current adjacent pair is bad, pay operation and skip the next pair, because this operation can cover both. That is the whole greedy.
Research checked: the supplied statement, the official Codeforces problem page, and the Codeforces Round 1080 tutorial/code at https://codeforces.com/blog/entry/151174. The official code uses the same greedy idea below; the statement remains the source of truth.
The die is simpler than it looks. Opposite faces are , , and , so two values are adjacent iff
So an adjacent pair is bad iff
Now look at the operation. Changing can only affect the two neighboring pairs:
So one operation can fix at most two bad adjacent pairs, and those two bad pairs must be consecutive. That already hints at the answer: scan bad edges and greedily cover them in chunks of size at most .
The only non-obvious part is this: when we find a bad pair , can we always spend one operation on and safely ignore the next pair too?
Yes. Suppose exists. We want to replace with some value such that both pairs are valid:
For to be valid, must not be
For to be valid, must not be
That bans at most values out of , so at least valid choices remain. If does not exist, it is even easier: just choose anything adjacent to .
So the greedy is:
This is not just vibes, it is optimal.
For the lower bound, consider the first bad pair not yet handled. Any valid final sequence must change at least one of its two endpoints, so we need at least one operation. Also, that one operation cannot affect anything beyond the next pair. Therefore after paying one operation for this bad pair, the best possible situation is exactly that the current pair and the next pair are both handled. The greedy does that, so it never wastes an operation.
Equivalently, bad adjacent pairs form runs, and a single changed element can cover at most two consecutive bad pairs. A run of length therefore needs at least operations, and the greedy takes exactly every other bad pair, giving for each run. Clean, no dice gymnastics required.
Edge cases:
The scan is linear. Each test case runs in
time and uses
extra memory.
#include <bits/stdc++.h>
using namespace std;
using ll = long long;
void setIO() {
ios::sync_with_stdio(false);
cin.tie(nullptr);
}
int main() {
setIO();
int T;
cin >> T;
while (T--) {
int n;
cin >> n;
vector<int> a(n);
for (int &x : a) cin >> x;
int ans = 0;
for (int i = 1; i < n; i++) {
if (a[i] == a[i - 1] || a[i] + a[i - 1] == 7) {
ans++;
i++;
}
}
cout << ans << '\n';
}
return 0;
}#include <bits/stdc++.h>
using namespace std;
using ll = long long;
void setIO() {
ios::sync_with_stdio(false);
cin.tie(nullptr);
}
int main() {
setIO();
int T;
cin >> T;
while (T--) {
int n;
cin >> n;
vector<int> a(n);
for (int &x : a) cin >> x;
int ans = 0;
for (int i = 1; i < n; i++) {
if (a[i] == a[i - 1] || a[i] + a[i - 1] == 7) {
ans++;
i++;
}
}
cout << ans << '\n';
}
return 0;
}