【比赛链接】
【题解链接】
【A】 Increasing by Modulo
【思路要点】
- 二分答案,贪心判断。
- 时间复杂度 O ( N L o g M ) O(NLogM) O(NLogM) 。
【代码】
#include<bits/stdc++.h> using namespace std; const int MAXN = 3e5 + 5; typedef long long ll; typedef long double ld; typedef unsigned long long ull; template <typename T> void chkmax(T &x, T y) { x = max(x, y); } template <typename T> void chkmin(T &x, T y) { x = min(x, y); } template <typename T> void read(T &x) { x = 0; int f = 1; char c = getchar(); for (; !isdigit(c); c = getchar()) if (c == '-') f = -f; for (; isdigit(c); c = getchar()) x = x * 10 + c - '0'; x *= f; } template <typename T> void write(T x) { if (x < 0) x = -x, putchar('-'); if (x > 9) write(x / 10); putchar(x % 10 + '0'); } template <typename T> void writeln(T x) { write(x); puts(""); } int n, m, a[MAXN]; bool valid(int mid) { int now = 0; for (int i = 1; i <= n; i++) { int tmp = (now - a[i] + m) % m; if (tmp <= mid) now = now; else if (a[i] >= now) now = a[i]; else return false; } return true; } int main() { read(n), read(m); for (int i = 1; i <= n; i++) read(a[i]); int l = 0, r = m; while (l < r) { int mid = (l + r) / 2; if (valid(mid)) r = mid; else l = mid + 1; } writeln(l); return 0; }
【B】 Good Triple
【思路要点】
- 搜索可知,长度大于等于 9 9 9 的字符串都可以找到一对 ( x , k ) (x,k) (x,k) 。
- 因此直接暴力即可,时间复杂度 O ( N ) O(N) O(N) 。
【代码】
#include<bits/stdc++.h> using namespace std; const int MAXN = 6e5 + 5; typedef long long ll; typedef long double ld; typedef unsigned long long ull; template <typename T> void chkmax(T &x, T y) { x = max(x, y); } template <typename T> void chkmin(T &x, T y) { x = min(x, y); } template <typename T> void read(T &x) { x = 0; int f = 1; char c = getchar(); for (; !isdigit(c); c = getchar()) if (c == '-') f = -f; for (; isdigit(c); c = getchar()) x = x * 10 + c - '0'; x *= f; } template <typename T> void write(T x) { if (x < 0) x = -x, putchar('-'); if (x > 9) write(x / 10); putchar(x % 10 + '0'); } template <typename T> void writeln(T x) { write(x); puts(""); } char s[MAXN]; int p[MAXN]; int main() { scanf("%s", s + 1); int n = strlen(s + 1); for (int i = 1; i <= n; i++) { for (int j = 1; j <= i - 1 && j <= n - i && j <= 9; j++) if (s[i + j] == s[i] && s[i - j] == s[i]) { chkmax(p[i + j], i - j); break; } } int now = 0; ll ans = 0; for (int i = 1; i <= n; i++) { chkmax(now, p[i]); ans += now; } writeln(ans); return 0; }
【C】 And Reachability
【思路要点】
- 记 d i s t i , p , q dist_{i,p,q} disti,p,q 表示由 i i i 处的 2 p 2^p 2p 位出发,最早可以达到 2 q 2^q 2q 位的位置。
- 可以直接由 d i s t i + 1 , p , ∗ dist_{i+1,p,*} disti+1,p,∗ 转移到 d i s t i , p , ∗ dist_{i,p,*} disti,p,∗ 。
- 时间复杂度 O ( N L o g 2 N + Q L o g N ) O(NLog^2N+QLogN) O(NLog2N+QLogN) 。
【代码】
#include<bits/stdc++.h> using namespace std; const int MAXN = 3e5 + 5; const int MAXLOG = 20; typedef long long ll; typedef long double ld; typedef unsigned long long ull; template <typename T> void chkmax(T &x, T y) { x = max(x, y); } template <typename T> void chkmin(T &x, T y) { x = min(x, y); } template <typename T> void read(T &x) { x = 0; int f = 1; char c = getchar(); for (; !isdigit(c); c = getchar()) if (c == '-') f = -f; for (; isdigit(c); c = getchar()) x = x * 10 + c - '0'; x *= f; } template <typename T> void write(T x) { if (x < 0) x = -x, putchar('-'); if (x > 9) write(x / 10); putchar(x % 10 + '0'); } template <typename T> void writeln(T x) { write(x); puts(""); } bool ans[MAXN]; int dist[MAXLOG]; int n, q, a[MAXN], bit[MAXLOG], mp[MAXLOG][MAXLOG