結果
問題 |
No.921 ずんだアロー
|
ユーザー |
![]() |
提出日時 | 2025-05-14 13:09:15 |
言語 | C++17 (gcc 13.3.0 + boost 1.87.0) |
結果 |
AC
|
実行時間 | 10 ms / 2,000 ms |
コード長 | 4,948 bytes |
コンパイル時間 | 627 ms |
コンパイル使用メモリ | 74,804 KB |
実行使用メモリ | 6,272 KB |
最終ジャッジ日時 | 2025-05-14 13:10:22 |
合計ジャッジ時間 | 1,856 ms |
ジャッジサーバーID (参考情報) |
judge1 / judge5 |
(要ログイン)
ファイルパターン | 結果 |
---|---|
sample | AC * 3 |
other | AC * 22 |
ソースコード
#include <iostream> #include <vector> #include <algorithm> // Use long long for DP states to prevent potential overflow, although unlikely given N <= 10^5. // The maximum count could theoretically be N, which fits within a standard 32-bit integer. // However, using long long is safer and doesn't significantly impact performance here. using ll = long long; int main() { // Optimize standard I/O operations for speed. std::ios_base::sync_with_stdio(false); std::cin.tie(NULL); int N; // Number of mochi std::cin >> N; // Handle edge case: N=0. If there are no mochi, the maximum count is 0. if (N == 0) { std::cout << 0 << std::endl; return 0; } // Read the sizes of the N mochi into a vector. std::vector<int> A(N); for (int i = 0; i < N; ++i) { std::cin >> A[i]; } // Handle edge case: N=1. If there is only one mochi, we can select it. Max count is 1. if (N == 1) { std::cout << 1 << std::endl; return 0; } // We use dynamic programming with constant space optimization. // We maintain two variables representing the DP states for the previous index `i-1`. // `prev_0`: stores the maximum count considering elements up to index `i-1`, // where the element at index `i-1` is NOT selected. // `prev_1`: stores the maximum count considering elements up to index `i-1`, // where the element at index `i-1` IS selected. ll prev_0 = 0; ll prev_1 = 0; // Initialize the DP states after conceptually processing the first element (at index 0). // Base case for index 0: // - If we don't select the mochi at index 0: Max count is 0. (This corresponds to `prev_0` for i=1) // - If we select the mochi at index 0: Max count is 1. (This corresponds to `prev_1` for i=1) prev_0 = 0; prev_1 = 1; // Iterate through the array starting from the second element (index 1) up to N-1. for (int i = 1; i < N; ++i) { // Calculate the DP states for the current index `i`. ll curr_0 = 0; // max count up to index `i`, with index `i` NOT selected. ll curr_1 = 0; // max count up to index `i`, with index `i` selected. // Calculate `curr_0`: maximum count up to index `i`, with `i` NOT selected. // If we don't select element `i`, the maximum count is simply the maximum possible count // achieved up to index `i-1`, regardless of whether `i-1` was selected or not selected. // This is the max of the two states from the previous step. curr_0 = std::max(prev_0, prev_1); // Calculate `curr_1`: maximum count up to index `i`, with `i` selected. // This decision depends on the sizes of mochi at indices `i` and `i-1`. // The problem states that if two adjacent zunda mochi have different sizes, the smaller one disappears. // To maximize the final count, we should select an initial set such that no mochi disappears. // This means if we select both mochi at `i` and `i-1`, their sizes must be equal (`A[i] == A[i-1]`). if (A[i] == A[i-1]) { // If sizes are equal, selecting `i` is compatible with selecting `i-1`. // We can transition from either state at `i-1`: // Case 1: Select `i`, after selecting `i-1`. The maximum score path ending with `i-1` selected is `prev_1`. Total score: `1 + prev_1`. // Case 2: Select `i`, after NOT selecting `i-1`. The maximum score path ending with `i-1` not selected is `prev_0`. Total score: `1 + prev_0`. // We take the maximum of these two possible transitions to get the best score ending with `i` selected. curr_1 = 1 + std::max(prev_0, prev_1); } else { // If sizes are different (`A[i] != A[i-1]`), we cannot select `i` if `i-1` was also selected, // because one of them would disappear, leading to a suboptimal count. // Therefore, to select `i`, we must NOT have selected `i-1`. // We must transition from the state where `i-1` was NOT selected (`prev_0`). // The total score is `1` (for selecting `i`) plus the max score ending at `i-1` not selected (`prev_0`). curr_1 = 1 + prev_0; } // Update the DP states for the next iteration (`i+1`). // The calculated current states (`curr_0`, `curr_1`) become the "previous" states for the next step. prev_0 = curr_0; prev_1 = curr_1; } // After iterating through all elements up to `N-1`, the final answer is the maximum // possible count achievable considering all N elements. This is the maximum of the two final states: // either the last element (at `N-1`) was selected (`prev_1`) or it was not selected (`prev_0`). std::cout << std::max(prev_0, prev_1) << std::endl; return 0; }