http://codeforces.com/gym/103202
H. The Boomsday Project
题意:共享单车,每次骑要花费 r 元。另外还有 n 种租赁方式,每种方式在购买后 di 天内有效,在有效期内能免费骑 ki 次,购买需要花费 ci 元。给出 m 条骑车记录,在第 pi 天骑了 qi 次,问最少花费。1≤n≤500,1≤m≤105,1≤r≤109,1≤di,ki,ci≤109,0≤pi≤109,0≤qi≤3×105,∑i=1mqi≤3×105
dp
构造一个新的数列,连续 qi 个 pi 代表在第 pi 天骑了 qi 次。
每种租赁方式就相当于一种块。对于一种租赁方式,有效期一定随着当前日期单调,所以只需要维护右端点位置即可。
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
| #include <bits/stdc++.h>
bool dbg = true; #define debug(x) if (dbg) cout << #x << ":\t" << (x) << endl; using namespace std; #define ll long long #define ull unsigned ll const int N = 1e6 + 10; const int INF = 0x3f3f3f3f; const ll inf = 0x3f3f3f3f3f3f3f3f; const ll mod = 998244353; const ll inv2 = (mod + 1) / 2; typedef pair<int, int> pii; typedef pair<int, ll> pil; typedef pair<ll, int> pli;
int n, m; ll r; int d[1010], b[1010]; ll c[1010]; pii t[N]; int a[N], pt[1010]; ll dp[N];
int main() { scanf("%d%d%lld", &m, &n, &r); for (int i = 1; i <= m; i++)scanf("%d%d%lld", &d[i], &b[i], &c[i]); for (int i = 1; i <= n; i++)scanf("%d%d", &t[i].first, &t[i].second); sort(t + 1, t + n + 1); int tot = 0; for (int i = 1; i <= n; i++) { for (int j = 1; j <= t[i].second; j++)a[++tot] = t[i].first; } n = tot; memset(dp, 0x3f, sizeof(dp)); dp[0] = 0; for (int i = 1; i <= n; i++) { dp[i] = min(dp[i], dp[i - 1] + r); for (int j = 1; j <= m; j++) { while (pt[j] - i + 1 <= b[j] && a[pt[j]] - a[i] + 1 <= d[j]) { pt[j]++; dp[pt[j] - 1] = min(dp[pt[j] - 1], dp[i - 1] + c[j]); } } } printf("%lld\n", dp[n]); return 0; }
|
D. Journey to Un’Goro
题意:定义一个字符串的值等于包含奇数个 ‘r’ 的连续子串的个数,问所有只由 ‘r’,‘b’ 构成的字符串中最大的值。并输出值等于最大值的字典序最小的前100个字符串。
dfs剪枝
区间 [i,j] 中包含奇数个 ‘r’,说明 pre[i−1] 与 pre[j] 异号,pre[i] 表示前 i 个字符中的 ‘r’ 的个数。
显然当 pre 数组中奇数值与偶数值相差不超过 1 个时最优。由于 pre 数组长度为 n+1,所以此时分别取 ⌊2n+1⌋ 与 ⌈2n+1⌉ 。
dfs时记录 pre 中奇数与偶数个数,当超过 ⌈2n+1⌉ 时剪枝。
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
| #include <bits/stdc++.h>
bool dbg = true; #define debug(x) if (dbg) cout << #x << ":\t" << (x) << endl; using namespace std; #define ll long long #define ull unsigned ll const int N = 1e6 + 10; const int INF = 0x3f3f3f3f; const ll inf = 0x3f3f3f3f3f3f3f3f; const ll mod = 998244353; const ll inv2 = (mod + 1) / 2; typedef pair<int, int> pii; typedef pair<int, ll> pil; typedef pair<ll, int> pli;
int n; int ans; char s[N];
void dfs(int dep, int c0, int c1, int st) { if (c0 > (n + 2) / 2 || c1 > (n + 2) / 2)return; if (dep > n) { printf("%s\n", s + 1); ans++; if (ans >= 100)exit(0); return; } s[dep] = 'b'; dfs(dep + 1, c0 + (st ^ 1), c1 + st, st); s[dep] = 'r'; st ^= 1; dfs(dep + 1, c0 + (st ^ 1), c1 + st, st); }
int main() { scanf("%d", &n); printf("%lld\n", 1ll * (n + 1) / 2 * ((n + 2) / 2)); dfs(1, 1, 0, 0); return 0; }
|