Submission #162837

#TimeUsernameProblemLanguageResultExecution timeMemory
162837rama_pangAliens (IOI16_aliens)C++14
60 / 100
2085 ms685076 KiB
#include "aliens.h" #include <bits/stdc++.h> #define NO_DEBUG using namespace std; using lint = long long; const lint INF = 1e15; struct Segment { lint left, right; Segment(lint l = 0, lint r = 0): left(l), right(r) {} bool operator < (const Segment &o) const { return left < o.left || (left == o.left && right > o.right); } bool operator == (const Segment &o) const { return left == o.left && right == o.right; } }; struct ConvexHull { // Convex Hull Trick struct Line { lint m, c; int id; Line(lint M = 0, lint C = INF, int id_ = -1): m(M), c(C), id(id_) {} lint get(lint x) { return m * x + c; } }; vector<Line> hull = {Line(0, INF)}; int ptr = 0; void insert(lint m, lint c) { hull.emplace_back(Line(m, c)); int sz = hull.size() - 1; /* y = m1x + c1 = m2x + c2 (m1 - m2)x = (c2 - c1) x = (c2 - c1) / (m1 - m2) (c2 - c1) / (m1 - m2) < (c3 - c2) / (m2 - m3) */ while (ptr <= sz - 2 && (hull[sz - 1].c - hull[sz].c) * (hull[sz - 1].m - hull[sz - 2].m) < (hull[sz - 2].c - hull[sz - 1].c) * (hull[sz].m - hull[sz - 1].m)) hull[sz - 1] = hull[sz], sz--, hull.pop_back(); } lint query(lint x) { while (ptr + 1 < hull.size() && hull[ptr].get(x) > hull[ptr + 1].get(x)) ptr++; return hull[ptr].get(x) + x * x; } }; int N, K; vector<Segment> segment; vector<vector<lint>> DP; vector<ConvexHull> hull; void preprocess(int n, int k, vector<int> r, vector<int> c) { for (int i = 0; i < n; i++) segment.emplace_back(min(r[i], c[i]), max(r[i], c[i])); sort(segment.begin(), segment.end()); vector<Segment> tmp; tmp.emplace_back(-1, -1); for (auto s : segment) { Segment overlap = Segment(min(tmp.back().left, s.left), max(tmp.back().right, s.right)); if (overlap == s) swap(s, tmp.back()); if (overlap == tmp.back()) continue; tmp.emplace_back(s); } segment = tmp, N = segment.size() - 1, K = k; DP.assign(N + 1, vector<lint>(K + 1, INF)); hull.resize(K + 1); } lint take_photos(int n, int m, int k, vector<int> r, vector<int> c) { preprocess(n, k, r, c); for (int k = 0; k <= K; k++) DP[0][k] = 0; for (int k = 1; k <= K; k++) { for (int n = 1; n <= N; n++) { lint m = - 2 * segment[n].left; lint c = + segment[n].left * segment[n].left - max(0ll, segment[n - 1].right - segment[n].left + 1) * max(0ll, segment[n - 1].right - segment[n].left + 1) + DP[n - 1][k - 1]; hull[k].insert(m, c); DP[n][k] = min(DP[n][k], hull[k].query(segment[n].right + 1)); } } #ifndef NO_DEBUG for (int i = 0; i <= K; i++) { cout << "K = " << i << ": "; for (int j = 0; j <= N; j++) { cout << DP[j][i] << " "; } cout << "\n"; } #endif return DP[N][K]; }

Compilation message (stderr)

aliens.cpp: In member function 'lint ConvexHull::query(lint)':
aliens.cpp:59:24: warning: comparison between signed and unsigned integer expressions [-Wsign-compare]
         while (ptr + 1 < hull.size() && hull[ptr].get(x) > hull[ptr + 1].get(x))
                ~~~~~~~~^~~~~~~~~~~~~
#Verdict Execution timeMemoryGrader output
Fetching results...
#Verdict Execution timeMemoryGrader output
Fetching results...
#Verdict Execution timeMemoryGrader output
Fetching results...
#Verdict Execution timeMemoryGrader output
Fetching results...
#Verdict Execution timeMemoryGrader output
Fetching results...
#Verdict Execution timeMemoryGrader output
Fetching results...