Submission #301427

#TimeUsernameProblemLanguageResultExecution timeMemory
301427KhongorCarnival Tickets (IOI20_tickets)C++14
27 / 100
1120 ms105832 KiB
#include "tickets.h" #include <bits/stdc++.h> using namespace std; vector<vector<int>> ans; // 1 5 // 10 10 // 8 12 // 12 20 // a1 a2 b1 c1 // b2 c2 d1 d2 // -a1 -b1 -c1 d2 // -a1 -b1 +c2 +d2 vector<vector<int>> p; vector<vector<bool>> used; long long bst; void rec(int k, int at, vector<vector<int>> &x) { if (at == p.size()) { vector<int> v; for (int i = 0; i < p.size(); i++) { for (auto idx: p[i]) { v.push_back(idx); } } sort(v.begin(), v.end()); long long cur = 0; for (int i = 0; i < v.size() / 2; i++) cur += v[v.size() - 1 - i] - v[i]; bst = max(bst, cur); return; } if (p[at].size() == k) { rec(k, at + 1, x); return; } for (int i = 0; i < x[at].size(); i++) if (!used[at][i]) { used[at][i] = true; p[at].push_back(x[at][i]); rec(k, at, x); p[at].pop_back(); used[at][i] = false; } } long long slow(int k, vector<vector<int>> x) { int n = x.size(); int m = x[0].size(); p = vector<vector<int>>(n); used = vector<vector<bool>>(n, vector<bool>(m, false)); bst = -1; rec(k, 0, x); return bst; } long long fast(int k, vector<vector<int>> x) { int n = x.size(); int m = x[0].size(); ans = vector<vector<int>>(n, vector<int>(m, -1)); long long res = 0; vector<pair<int, pair<int, int>>> all; bool binary = true; for (int i = 0; i < n; i++) for (int j = 0; j < m; j++) { all.push_back({x[i][j], {i, j}}); } sort(all.begin(), all.end()); vector<vector<pair<int, int>>> high(n), pickedLow(n), pickedHigh(n); int median = (all[n * m / 2].first + all[n * m / 2 - 1].first) / 2; assert(all[n * m / 2].first != all[n * m / 2 - 1].first); int cnt = 0; for (int i = 0; i < all.size(); i++) { int color = all[i].second.first; int ticket = all[i].second.second; if (i < all.size() / 2) { if (pickedLow[color].size() < k) { pickedLow[color].push_back({median - all[i].first, ticket}); cnt++; res += median - all[i].first; } } else { high[color].push_back({all[i].first - median, ticket}); } } for (int i = 0; i < n; i++) { while (pickedLow[i].size() + pickedHigh[i].size() < k) { res += high[i].back().first; pickedHigh[i].push_back(high[i].back()); high[i].pop_back(); } } vector<vector<long long>> b(n); int need = cnt - n * k / 2; for (int i = 0; i < n; i++) { long long s = 0; b[i].push_back(0); for (int j = 1; j <= min(pickedLow[i].size(), high[i].size()); j++) { s += high[i][high[i].size() - j].first - pickedLow[i][pickedLow[i].size() - j].first; b[i].push_back(s); } } long long inf = -(1LL << 62); vector<vector<long long>> dp(n + 1, vector<long long>(need + 1, inf)); dp[0][0] = 0; vector<vector<int>> back(n + 1, vector<int>(need + 1)); for (int i = 0; i < n; i++) { for (int j = 0; j <= need; j++) { if (dp[i][j] == inf) continue; for (int k = 0; k < b[i].size(); k++) { if (j + k > need) break; if (dp[i][j] + b[i][k] > dp[i + 1][k + j]) { dp[i + 1][k + j] = dp[i][j] + b[i][k]; back[i + 1][k + j] = k; } } } } res += dp[n][need]; for (int i = n - 1; i >= 0; i--) { int k = back[i + 1][need]; need -= k; for (int j = 0; j < k; j++) { pickedLow[i].pop_back(); pickedHigh[i].push_back(high[i].back()); high[i].pop_back(); } } // vector<int> at(n, 0); // while (need--) { // int idx = -1, best = 0; // for (int i = 0; i < n; i++) { // if (at[i] == b[i].size()) continue; // int cur; // cur = b[i][at[i]]; // if (idx == -1 || cur > best) { // best = cur; // idx = i; // } // } // assert(idx != -1); // // switch // res += best; // at[idx]++; // pickedLow[idx].pop_back(); // pickedHigh[idx].push_back(high[idx].back()); // high[idx].pop_back(); // } // construct for (int r = 0; r < k; r++) { vector<bool> used(n); vector<pair<int, int>> counts; for (int i = 0; i < n; i++) counts.push_back({pickedLow[i].size(), i}); sort(counts.rbegin(), counts.rend()); int taken = 0; for (int ii = 0; ii < n; ii++) { int i = counts[ii].second; if (pickedLow[i].size() > 0) { used[i] = true; taken++; ans[i][pickedLow[i].back().second] = r; pickedLow[i].pop_back(); } if (taken == n / 2) break; } taken = 0; for (int i = 0; i < n; i++) { if (pickedHigh[i].size() > 0 && !used[i]) { taken++; ans[i][pickedHigh[i].back().second] = r; pickedHigh[i].pop_back(); } if (taken == n / 2) break; } } allocate_tickets(ans); return res; } long long find_maximum(int k, std::vector<std::vector<int>> x) { return fast(k, x); // srand(time(NULL)); // for (int test = 1; test <= 100; test++) { // int n = 4; // int m = 3; // vector<vector<int>> v = {{1, 1, 1}, {1, 0, 1}, {1, 1, 1}, {1, 0, 0}}; // cout << fast(2, v) << endl; // exit(0); // // for (int i = 0; i < n; i++) for (int j = 0; j < m; j++) v[i][j] = rand() % 2; // if (slow(2, v) != fast(2, v)) { // cout << slow(2, v) << " " << fast(2, v) << endl; // for (int i = 0; i < n; i++) { // for (auto j : v[i]) { // cout << j << " "; // } // cout << endl; // } // exit(-1); // } // } // return 0; } // a b a c // c b d d

Compilation message (stderr)

tickets.cpp: In function 'void rec(int, int, std::vector<std::vector<int> >&)':
tickets.cpp:23:9: warning: comparison of integer expressions of different signedness: 'int' and 'std::vector<std::vector<int> >::size_type' {aka 'long unsigned int'} [-Wsign-compare]
   23 |  if (at == p.size()) {
      |      ~~~^~~~~~~~~~~
tickets.cpp:25:21: warning: comparison of integer expressions of different signedness: 'int' and 'std::vector<std::vector<int> >::size_type' {aka 'long unsigned int'} [-Wsign-compare]
   25 |   for (int i = 0; i < p.size(); i++) {
      |                   ~~^~~~~~~~~~
tickets.cpp:32:21: warning: comparison of integer expressions of different signedness: 'int' and 'std::vector<int>::size_type' {aka 'long unsigned int'} [-Wsign-compare]
   32 |   for (int i = 0; i < v.size() / 2; i++)
      |                   ~~^~~~~~~~~~~~~~
tickets.cpp:37:19: warning: comparison of integer expressions of different signedness: 'std::vector<int>::size_type' {aka 'long unsigned int'} and 'int' [-Wsign-compare]
   37 |  if (p[at].size() == k) {
      |      ~~~~~~~~~~~~~^~~~
tickets.cpp:41:20: warning: comparison of integer expressions of different signedness: 'int' and 'std::vector<int>::size_type' {aka 'long unsigned int'} [-Wsign-compare]
   41 |  for (int i = 0; i < x[at].size(); i++)
      |                  ~~^~~~~~~~~~~~~~
tickets.cpp: In function 'long long int fast(int, std::vector<std::vector<int> >)':
tickets.cpp:79:20: warning: comparison of integer expressions of different signedness: 'int' and 'std::vector<std::pair<int, std::pair<int, int> > >::size_type' {aka 'long unsigned int'} [-Wsign-compare]
   79 |  for (int i = 0; i < all.size(); i++) {
      |                  ~~^~~~~~~~~~~~
tickets.cpp:82:9: warning: comparison of integer expressions of different signedness: 'int' and 'std::vector<std::pair<int, std::pair<int, int> > >::size_type' {aka 'long unsigned int'} [-Wsign-compare]
   82 |   if (i < all.size() / 2) {
      |       ~~^~~~~~~~~~~~~~~~
tickets.cpp:83:32: warning: comparison of integer expressions of different signedness: 'std::vector<std::pair<int, int> >::size_type' {aka 'long unsigned int'} and 'int' [-Wsign-compare]
   83 |    if (pickedLow[color].size() < k) {
      |        ~~~~~~~~~~~~~~~~~~~~~~~~^~~
tickets.cpp:94:53: warning: comparison of integer expressions of different signedness: 'std::vector<std::pair<int, int> >::size_type' {aka 'long unsigned int'} and 'int' [-Wsign-compare]
   94 |   while (pickedLow[i].size() + pickedHigh[i].size() < k) {
      |          ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~^~~
tickets.cpp:106:21: warning: comparison of integer expressions of different signedness: 'int' and 'const long unsigned int' [-Wsign-compare]
  106 |   for (int j = 1; j <= min(pickedLow[i].size(), high[i].size()); j++) {
      |                   ~~^~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
tickets.cpp:119:22: warning: comparison of integer expressions of different signedness: 'int' and 'std::vector<long long int>::size_type' {aka 'long unsigned int'} [-Wsign-compare]
  119 |    for (int k = 0; k < b[i].size(); k++) {
      |                    ~~^~~~~~~~~~~~~
tickets.cpp:68:7: warning: unused variable 'binary' [-Wunused-variable]
   68 |  bool binary = true;
      |       ^~~~~~
#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...
#Verdict Execution timeMemoryGrader output
Fetching results...