|
1 | 1 | # Changelog for Jikka |
2 | 2 |
|
| 3 | +## 2021-07-21: v5.0.11.0 |
| 4 | + |
| 5 | +Convex Hull Trick and Segment Trees are implemented. |
| 6 | + |
| 7 | +Input (`examples/dp_z.py`): |
| 8 | + |
| 9 | +```python |
| 10 | +# https://atcoder.jp/contests/dp/tasks/dp_z |
| 11 | +from typing import * |
| 12 | + |
| 13 | +INF = 10 ** 18 |
| 14 | + |
| 15 | +def solve(n: int, c: int, h: List[int]) -> int: |
| 16 | + assert 2 <= n <= 10 ** 5 |
| 17 | + assert 1 <= c <= 10 ** 12 |
| 18 | + assert len(h) == n |
| 19 | + assert all(1 <= h_i <= 10 ** 6 for h_i in h) |
| 20 | + |
| 21 | + dp = [INF for _ in range(n)] |
| 22 | + dp[0] = 0 |
| 23 | + for i in range(1, n): |
| 24 | + for j in range(i): |
| 25 | + dp[i] = min(dp[i], dp[j] + (h[j] - h[i]) ** 2 + c) |
| 26 | + return dp[n - 1] |
| 27 | + |
| 28 | +def main() -> None: |
| 29 | + n, c = map(int, input().split()) |
| 30 | + h = list(map(int, input().split())) |
| 31 | + assert len(h) == n |
| 32 | + ans = solve(n, c, h) |
| 33 | + print(ans) |
| 34 | + |
| 35 | +if __name__ == '__main__': |
| 36 | + main() |
| 37 | +``` |
| 38 | + |
| 39 | +Output (<https://atcoder.jp/contests/dp/submissions/24563891>): |
| 40 | + |
| 41 | +```c++ |
| 42 | +#include "jikka/base.hpp" |
| 43 | +#include "jikka/convex_hull_trick.hpp" |
| 44 | +#include <algorithm> |
| 45 | +#include <array> |
| 46 | +#include <cstdint> |
| 47 | +#include <functional> |
| 48 | +#include <iostream> |
| 49 | +#include <numeric> |
| 50 | +#include <string> |
| 51 | +#include <tuple> |
| 52 | +#include <vector> |
| 53 | +int64_t solve(int64_t n_0, int64_t c_1, std::vector<int64_t> h_2) { |
| 54 | + std::vector<int64_t> x3; |
| 55 | + x3.push_back(0); |
| 56 | + jikka::convex_hull_trick x4_10; |
| 57 | + for (int32_t x5 = 0; x5 < n_0 - 1; ++x5) { |
| 58 | + x4_10.add_line(h_2[x5], h_2[x5] * h_2[x5] + x3[x5]); |
| 59 | + x3.push_back(c_1 + h_2[(x5 + 1)] * h_2[(x5 + 1)] + |
| 60 | + x4_10.get_min(h_2[(x5 + 1)] * -2)); |
| 61 | + } |
| 62 | + return x3[(n_0 - 1)]; |
| 63 | +} |
| 64 | +int main() { |
| 65 | + int64_t n_12 = -1; |
| 66 | + int64_t c_13 = -1; |
| 67 | + std::cin >> n_12; |
| 68 | + std::vector<int64_t> h_14(n_12, -1); |
| 69 | + std::cin >> c_13; |
| 70 | + for (int32_t i15 = 0; i15 < n_12; ++i15) { |
| 71 | + std::cin >> h_14[i15]; |
| 72 | + } |
| 73 | + auto ans_16 = solve(n_12, c_13, h_14); |
| 74 | + std::cout << ans_16 << ' '; |
| 75 | + std::cout << '\n' << ' '; |
| 76 | +} |
| 77 | +``` |
| 78 | +
|
| 79 | +Input (`examples/dp_q.py`): |
| 80 | +
|
| 81 | +```python |
| 82 | +# https://atcoder.jp/contests/dp/tasks/dp_q |
| 83 | +from typing import * |
| 84 | +
|
| 85 | +def solve(n: int, h: List[int], a: List[int]) -> int: |
| 86 | + assert 1 <= n <= 2 * 10 ** 5 |
| 87 | + assert len(h) == n |
| 88 | + assert all(1 <= h_i <= n for h_i in h) |
| 89 | + assert len(a) == n |
| 90 | + assert all(1 <= a_i <= 10 ** 9 for a_i in a) |
| 91 | +
|
| 92 | + dp = [0 for _ in range(n)] |
| 93 | + for i in range(n): |
| 94 | + b = 0 |
| 95 | + for j in range(h[i]): |
| 96 | + b = max(b, dp[j]) |
| 97 | + dp[h[i] - 1] = b + a[i] |
| 98 | + return max(dp) |
| 99 | +
|
| 100 | +def main() -> None: |
| 101 | + n = int(input()) |
| 102 | + h = list(map(int, input().split())) |
| 103 | + assert len(h) == n |
| 104 | + a = list(map(int, input().split())) |
| 105 | + assert len(a) == n |
| 106 | + ans = solve(n, h, a) |
| 107 | + print(ans) |
| 108 | +
|
| 109 | +if __name__ == '__main__': |
| 110 | + main() |
| 111 | +``` |
| 112 | + |
| 113 | +Output (<https://atcoder.jp/contests/dp/submissions/24561829>): |
| 114 | + |
| 115 | +```c++ |
| 116 | +#include "jikka/base.hpp" |
| 117 | +#include "jikka/segment_tree.hpp" |
| 118 | +#include <algorithm> |
| 119 | +#include <array> |
| 120 | +#include <atcoder/segtree> |
| 121 | +#include <cstdint> |
| 122 | +#include <functional> |
| 123 | +#include <iostream> |
| 124 | +#include <numeric> |
| 125 | +#include <string> |
| 126 | +#include <tuple> |
| 127 | +#include <vector> |
| 128 | +int64_t solve(int64_t n_0, std::vector<int64_t> h_1, std::vector<int64_t> a_2) { |
| 129 | + std::vector<int64_t> x4(n_0, 0); |
| 130 | + atcoder::segtree<int64_t, jikka::max_int64_t, jikka::const_int64_min> x5_13( |
| 131 | + x4); |
| 132 | + for (int32_t x6 = 0; x6 < n_0; ++x6) { |
| 133 | + x4[(h_1[x6] - 1)] = std::max<int64_t>(0, x5_13.prod(0, h_1[x6])) + a_2[x6]; |
| 134 | + x5_13.set(h_1[x6] - 1, x4[(h_1[x6] - 1)]); |
| 135 | + } |
| 136 | + int64_t x11 = *std::max_element(x4.begin(), x4.end()); |
| 137 | + return x11; |
| 138 | +} |
| 139 | +int main() { |
| 140 | + int64_t n_14 = -1; |
| 141 | + std::cin >> n_14; |
| 142 | + std::vector<int64_t> h_15(n_14, -1); |
| 143 | + std::vector<int64_t> a_16(n_14, -1); |
| 144 | + for (int32_t i17 = 0; i17 < n_14; ++i17) { |
| 145 | + std::cin >> h_15[i17]; |
| 146 | + } |
| 147 | + for (int32_t i18 = 0; i18 < n_14; ++i18) { |
| 148 | + std::cin >> a_16[i18]; |
| 149 | + } |
| 150 | + auto ans_19 = solve(n_14, h_15, a_16); |
| 151 | + std::cout << ans_19 << ' '; |
| 152 | + std::cout << '\n' << ' '; |
| 153 | +} |
| 154 | +``` |
| 155 | +
|
| 156 | +
|
3 | 157 | ## 2021-07-21: v5.0.10.0 |
4 | 158 |
|
5 | 159 | - The generated C++ code is optimized. |
|
0 commit comments