QOJ.ac
QOJ
ID | Problem | Submitter | Result | Time | Memory | Language | File size | Submit time | Judge time |
---|---|---|---|---|---|---|---|---|---|
#298238 | #6794. Sequence to Sequence | ucup-team087# | WA | 130ms | 5016kb | C++14 | 7.0kb | 2024-01-05 21:06:22 | 2024-01-05 21:06:23 |
Judging History
answer
#include <cassert>
#include <cmath>
#include <cstdint>
#include <cstdio>
#include <cstdlib>
#include <cstring>
#include <algorithm>
#include <bitset>
#include <complex>
#include <deque>
#include <functional>
#include <iostream>
#include <limits>
#include <map>
#include <numeric>
#include <queue>
#include <random>
#include <set>
#include <sstream>
#include <string>
#include <unordered_map>
#include <unordered_set>
#include <utility>
#include <vector>
using namespace std;
using Int = long long;
template <class T1, class T2> ostream &operator<<(ostream &os, const pair<T1, T2> &a) { return os << "(" << a.first << ", " << a.second << ")"; };
template <class T> ostream &operator<<(ostream &os, const vector<T> &as) { const int sz = as.size(); os << "["; for (int i = 0; i < sz; ++i) { if (i >= 256) { os << ", ..."; break; } if (i > 0) { os << ", "; } os << as[i]; } return os << "]"; }
template <class T> void pv(T a, T b) { for (T i = a; i != b; ++i) cerr << *i << " "; cerr << endl; }
template <class T> bool chmin(T &t, const T &f) { if (t > f) { t = f; return true; } return false; }
template <class T> bool chmax(T &t, const T &f) { if (t < f) { t = f; return true; } return false; }
#define COLOR(s) ("\x1b[" s "m")
unsigned xrand() {
static unsigned x = 314159265, y = 358979323, z = 846264338, w = 327950288;
unsigned t = x ^ x << 11; x = y; y = z; z = w; return w = w ^ w >> 19 ^ t ^ t >> 8;
}
constexpr Int INF = 1001001001001001001LL;
Int slow(const vector<Int> &A, const vector<Int> &B) {
Int ans = 0;
auto as = A, bs = B;
auto isBad = [&](int i) -> bool {
return (as[i] == 1 && bs[i]);
};
auto rel = [&](int i) -> Int {
return (0 <= i && i < (int)as.size()) ? (as[i] - bs[i]) : 0;
};
for (; ; ) {
const int n = as.size();
int im = -1;
for (int i = 0; i < n; ++i) if (!bs[i]) {
im = i;
break;
}
if (!~im) {
break;
}
int l0 = im, r0 = im + 1;
for (; l0 > 0 && !isBad(l0 - 1); --l0) {}
for (; r0 < n && !isBad(r0); ++r0) {}
int l = -1, r = -1;
for (int i = l0; i <= im; ++i) if (rel(i - 1) < rel(i)) {
l = i;
break;
}
for (int i = r0; i >= im + 1; --i) if (rel(i - 1) > rel(i)) {
r = i;
break;
}
assert(~l);
assert(~r);
// sub 1 from [l, r)
++ans;
for (int i = l; i < r; ++i) --as[i];
vector<Int> aas, bbs;
for (int i = 0; i < n; ++i) if (as[i]) {
aas.push_back(as[i]);
bbs.push_back(bs[i]);
}
as.swap(aas);
bs.swap(bbs);
}
{
const int n = as.size();
for (int i = 0; i <= n; ++i) if (rel(i - 1) < rel(i)) {
ans += (rel(i) - rel(i - 1));
}
}
return ans;
}
/*
slow strategy in order:
-1 x[l,r] times
ignore B[i]=0
+1 y[l,r] times
-1 z[l,r] times
min. \sum x[l,r] + \sum y[l,r] + \sum z[l,r]
sub. to
x, y, z >= 0
if B[i] > 0:
A[i] - \sum x[l,r] >= 1
A[i] - \sum x[l,r] + \sum y[l,r] - \sum z[l,r] = B[i]
if B[i] = 0:
A[i] - \sum x[l,r] <= 0
dual
B[i] > 0: p[i], q[i]
B[i] = 0: r[i]
max. \sum (1-A[i]) p[i] + \sum (B[i]-A[i]) q[i] + \sum (0-A[i]) r[i]
sub. to
p >= 0
r <= 0
\sum[i] (-p[i]) + \sum[i] (-q[i]) + \sum[i] (-r[i]) <= 1
\sum[i] q[i] <= 1
\sum[i] (-q[i]) <= 1
*/
Int fast(const vector<Int> &A, const vector<Int> &B) {
const int N = A.size();
for (int i = 0; i < N; ++i) if (!A[i] && B[i]) {
return -1;
}
// state: max suffix
Int crt[2][2][2];
for (int x = 0; x <= 1; ++x) for (int y = 0; y <= 1; ++y) for (int z = 0; z <= 1; ++z) {
crt[x][y][z] = -INF;
}
crt[0][0][0] = 0;
for (int i = 0; i < N; ++i) {
Int nxt[2][2][2];
for (int x = 0; x <= 1; ++x) for (int y = 0; y <= 1; ++y) for (int z = 0; z <= 1; ++z) {
nxt[x][y][z] = -INF;
}
if (B[i]) {
for (int x = 0; x <= 1; ++x) for (int y = 0; y <= 1; ++y) for (int z = 0; z <= 1; ++z) {
for (int p = 0; p <= 1; ++p) for (int q = -1; q <= 1; ++q) {
const int xx = max(x - p - q, 0);
const int yy = max(y + q, 0);
const int zz = max(z - q, 0);
if (xx <= 1 && yy <= 1 && zz <= 1) {
chmax(nxt[xx][yy][zz], crt[x][y][z] + (1 - A[i]) * p + (B[i] - A[i]) * q);
}
}
}
} else {
for (int x = 0; x <= 1; ++x) for (int y = 0; y <= 1; ++y) for (int z = 0; z <= 1; ++z) {
for (int r = -1; r <= 0; ++r) {
const int xx = max(x - r, 0);
if (xx <= 1) {
chmax(nxt[xx][y][z], crt[x][y][z] + (0 - A[i]) * r);
}
}
}
}
memcpy(crt, nxt, sizeof(nxt));
}
Int ans = -INF;
for (int x = 0; x <= 1; ++x) for (int y = 0; y <= 1; ++y) for (int z = 0; z <= 1; ++z) {
chmax(ans, crt[x][y][z]);
}
return ans;
}
/*
HELP
[1, 4, 2, 3, 3, 1, 1] [2, 0, 0, 1, 0, 0, 2]: 7 7 6
[3, 2, 2, 3, 2] [4, 0, 1, 0, 3]: 6 6 5
*/
void stress() {
constexpr int lim = 4;
for (int iter = 1; ; ++iter) {
const int n = 1 + xrand() % 5;
vector<Int> ini(n);
for (int i = 0; i < n; ++i) {
ini[i] = 1 + xrand() % lim;
}
cerr<<"iter = "<<iter<<", ini = "<<ini<<endl;
queue<vector<Int>> que;
map<vector<Int>, int> dist;
dist[ini] = 0;
que.push(ini);
for (; que.size(); ) {
const auto as = que.front();
que.pop();
const int c = dist[as];
for (const int sig : {+1, -1}) {
for (int l = 0; l <= n; ++l) for (int r = l + 1; r <= n; ++r) {
auto bs = as;
bool ok = true;
for (int i = l; i < r; ++i) if (as[i]) {
bs[i] += sig;
ok = ok && (0 <= bs[i] && bs[i] <= lim + 1);
}
if (ok) {
auto it = dist.find(bs);
if (it != dist.end() && it->first == bs) {
//
} else {
dist[bs] = c + 1;
que.push(bs);
}
}
}
}
}
for (const auto &kv : dist) {
const auto tar = kv.first;
bool ok = true;
for (int i = 0; i < n; ++i) {
ok = ok && (0 <= tar[i] && tar[i] <= lim);
}
if (ok) {
const auto slw = slow(ini, tar);
const auto fst = fast(ini, tar);
if (kv.second != slw || kv.second != fst) {
cerr << ini << " " << tar << ": " << kv.second << " " << slw << " " << fst << endl;
}
assert(kv.second == slw);
assert(kv.second == fst);
}
}
}
}
int main() {
// stress();
for (int numCases; ~scanf("%d", &numCases); ) { for (int caseId = 1; caseId <= numCases; ++caseId) {
int N;
scanf("%d", &N);
vector<Int> A(N); for (int i = 0; i < N; ++i) scanf("%lld", &A[i]);
vector<Int> B(N); for (int i = 0; i < N; ++i) scanf("%lld", &B[i]);
const Int ans = fast(A, B);
printf("%lld\n", ans);
}
#ifndef LOCAL
break;
#endif
}
return 0;
}
Details
Tip: Click on the bar to expand more detailed information
Test #1:
score: 100
Accepted
time: 0ms
memory: 4012kb
input:
2 5 1 1 1 1 1 2 0 2 0 2 7 3 1 2 3 2 1 4 2 0 0 0 0 0 2
output:
3 3
result:
ok 2 tokens
Test #2:
score: -100
Wrong Answer
time: 130ms
memory: 5016kb
input:
110121 5 0 0 0 0 0 1 4 5 4 1 5 1 0 0 0 0 0 6 8 6 1 5 2 0 0 0 0 4 4 1 3 6 5 3 0 0 0 0 5 1 1 7 6 5 4 0 0 0 0 6 8 7 0 8 5 5 0 0 0 0 5 9 7 7 5 5 6 0 0 0 0 9 2 2 8 0 5 7 0 0 0 0 9 4 7 0 9 5 8 0 0 0 0 6 7 3 7 5 5 9 0 0 0 0 4 0 9 1 4 5 0 1 0 0 0 0 6 6 3 0 5 1 1 0 0 0 3 4 3 4 9 5 2 1 0 0 0 0 4 0 1 4 5 3 1 0...
output:
-1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 ...
result:
wrong answer 19126th words differ - expected: '17', found: '15'