#include <algorithm>
#include <cstdio>
#include <vector>
#define lli long long int
#define FOR(i,a,b) for(int i=(int)(a); i<(int)(b); ++i)
#define MAX 500000
using namespace std;
int n, c;
vector<int> a, w, last_seen;
vector<lli> best_for_color;
int main() {
// Read data
scanf("%d %d", &n, &c);
a.resize(n); w.resize(n);
last_seen.resize(MAX+1, -1);
best_for_color.resize(MAX+1, 0);
FOR(i,0,n) scanf("%d %d", &a[i], &w[i]);
reverse(a.begin(), a.end());
reverse(w.begin(), w.end());
// Go through phases (bricks with the same size)
lli max_for_prev_phase = 0;
int end_pos, start_pos = 0;
while (start_pos < n) {
// Calculate phase boundaries
end_pos = start_pos;
while (end_pos < n && a[end_pos] == a[start_pos]) ++end_pos;
// Check all bricks with the same size
lli max_for_this_phase = 0;
int size = a[start_pos];
FOR(pos,start_pos,end_pos){
int color = w[pos];
// Already seen brick with the same size and color
if (size == last_seen[color]) continue;
// Choose best case
lli res = max(best_for_color[color] + size, max_for_prev_phase + size - c);
// Update brick variables
if (max_for_this_phase < res) max_for_this_phase = res;
best_for_color[color] = res;
last_seen[color] = size;
}
// Update phase variables
start_pos = end_pos;
if (max_for_prev_phase < max_for_this_phase) max_for_prev_phase = max_for_this_phase;
}
lli result = 0;
FOR(i,0,MAX+1) if (result < best_for_color[i]) result = best_for_color[i];
printf("%llu\n", result);
}
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 | #include <algorithm> #include <cstdio> #include <vector> #define lli long long int #define FOR(i,a,b) for(int i=(int)(a); i<(int)(b); ++i) #define MAX 500000 using namespace std; int n, c; vector<int> a, w, last_seen; vector<lli> best_for_color; int main() { // Read data scanf("%d %d", &n, &c); a.resize(n); w.resize(n); last_seen.resize(MAX+1, -1); best_for_color.resize(MAX+1, 0); FOR(i,0,n) scanf("%d %d", &a[i], &w[i]); reverse(a.begin(), a.end()); reverse(w.begin(), w.end()); // Go through phases (bricks with the same size) lli max_for_prev_phase = 0; int end_pos, start_pos = 0; while (start_pos < n) { // Calculate phase boundaries end_pos = start_pos; while (end_pos < n && a[end_pos] == a[start_pos]) ++end_pos; // Check all bricks with the same size lli max_for_this_phase = 0; int size = a[start_pos]; FOR(pos,start_pos,end_pos){ int color = w[pos]; // Already seen brick with the same size and color if (size == last_seen[color]) continue; // Choose best case lli res = max(best_for_color[color] + size, max_for_prev_phase + size - c); // Update brick variables if (max_for_this_phase < res) max_for_this_phase = res; best_for_color[color] = res; last_seen[color] = size; } // Update phase variables start_pos = end_pos; if (max_for_prev_phase < max_for_this_phase) max_for_prev_phase = max_for_this_phase; } lli result = 0; FOR(i,0,MAX+1) if (result < best_for_color[i]) result = best_for_color[i]; printf("%llu\n", result); } |
English