A - Add and Divide
1485A - Add and Divide
操作1:b++;操作2:a/b 问最少多少步操作 s.t. a->0
Solution
除非b=1,否则a最多30多步就可以到0,那么b操作最多进行30多次。而且肯定是b越早加越好,那么枚举b的次数算出总次数取最小值即可
Code
#include <bits/stdc++.h> using namespace std; #define ll long long const int maxn = 1e5 + 10; const int Max = 1e5 + 10; void solve() { int a, b; scanf("%d %d", &a, &b); if(b >= Max) { int sum = 0; while(a) { a /= b; sum++; } printf("%d ", sum); return; } int mmin = 1000000000; int xxx = 0; if(b == 1) { ++b; xxx = 1; } for (int i = b; i <= Max; ++ i) { int xx = i - b; int temp = a ; int sum = xx; while(temp) { temp /= i; sum++; } if(sum < mmin) { mmin = sum; } } printf("%d ", mmin+xxx); } int main() { int t; scanf("%d", &t); while (t--) { solve(); } return 0; }
B - Replace and Keep Sorted
1485B - Replace and Keep Sorted
定义两个数组是相似的当且仅当
- 都严格递增
- 两者长度相同
- 所有元素在1到k之间(闭区间)
- 两个数组只恰好在一个位置不同
给定q个询问,每个询问给出[l,r],求对于子数组[l,r]部分有多少个与k相似的数组
Solution
限制条件贼多,统计一下即可
Code
#include <bits/stdc++.h> using namespace std; #define ll long long #define inf 0x3f3f3f3f const int maxn = 1e5 + 10; int t, n, q, k, l[maxn], r[maxn], a[maxn], sum[maxn]; void solve() { scanf("%d %d %d", &n, &q, &k); for(int i = 1; i <= n; ++ i) scanf("%d", &a[i]); l[1] = a[1] - 1; r[n] = k - a[n]; for (int i = 2; i <= n; ++ i) { l[i] = a[i] - a[i - 1] - 1; } for (int i = n - 1; i >= 1; -- i) r[i] = a[i + 1] - a[i] - 1; // for (int i = 1; i <= n; ++ i) // printf("%d %d ", l[i], r[i]); for (int i = 1; i <= n; ++ i) sum[i] = sum[i - 1] + l[i] + r[i]; while (q--) { int L, R; scanf("%d %d", &L, &R); printf("%d ", sum[R] - sum[L - 1] + a[L] - 1 + k - a[R] - l[L] - r[R]); } } int main() { solve(); return 0; }
C - Floor and Mod
1485C - Floor and Mod
定义一组数对(x,y)为特殊的当且仅当 x/y = x%y
然后给定x,y。a∈[1,x] ,b∈[1.y] 问有多少对符合条件的数对(a,b)
Solution
打表可得,发现固定的b所对应的答案数前一段属于等差数列,后一段是非递增序列而且连续相等的数特性很明显,那么分块,我不会,还是写二分吧。
Code
#include<bits/stdc++.h> #define ll long long int t, x, y; int get(int x,int b) { if (1ll * b * b - 1 <= x) return b - 1; int ans = x / b; if (x < ans * b + ans) ans--; return ans; } int main() { scanf("%d", &t); while (t--) { scanf("%d %d", &x, &y); ll ans = 0; int p = 1; for (int i = 1; i <= y; i++) { if (get(x, i) == i - 1) { ans += i - 1; p++; } else break; } for (int l = p, r; l <= y; l = r + 1) { int now = get(x, l); int ll = l, rr = y; int ans1; while (ll <= rr) { int mid = ll + rr >> 1; if (get(x, mid) == now) { ans1 = mid; ll = mid + 1; } else rr = mid - 1; } r = ans1; ans += 1ll * now * (r - l + 1); } printf("%lld ", ans); } return 0; }
D - Multiples and Power Differences
1485D - Replace and Keep Sorted
给定n ∗ m 的矩阵A,要求构造出一个n ∗ m 的矩阵B,满足
-
所有元素小于1e6
-
矩阵B是矩阵A对应元素的倍数
-
矩阵B 中每个元素与相邻任何元素(有共边)之差的绝对值必须是某个正整数的四次方
Solution
构造,我们发现720720是lcm(1~16) < 1e6,当所有的bi,j都是720720时,第一个和第二个条件满足了,但不满足第三个条件,那么我们只需要黑白染色中任选一个颜色填入720720,另一个颜色填入720720+矩阵A元素的四次方,这样即可满足所有条件。
Code
#include<bits/stdc++.h> #define ll long long const int xx = 720720; int main() { int n, m; scanf("%d %d", &n, &m); for (int i = 1; i <= n; ++ i) { for (int j = 1; j <= m; ++ j) { int temp; scanf("%d", &temp); if((i+j)&1) printf("720720"); else printf("%d", 720720 + temp * temp * temp * temp); printf("%c", j == m ? ' ' : ' '); } } return 0; }
E - Move and Swap
1485E - Move and Swap
Solution
Code
F - Copy or Prefix Sum
1485F - Copy or Prefix Sum
Solution
Code