补题链接:Here

1514A. Perfectly Imperfect Array

题意:给定长度为 Codeforces Round #716 (Div. 2) A ~ D 个人题解 - 图1Codeforces Round #716 (Div. 2) A ~ D 个人题解 - 图2 序列,请问是否存在子序列积不存在平方根

思路:子序列的话,一个元素也是子序列,那么只要存在某个元素不存在平方根即可

  1. void solve() {
  2. int n;
  3. cin >> n;
  4. bool f = 1;
  5. while (n--) {
  6. int x, tmp;
  7. cin >> x;
  8. tmp = sqrt(x);
  9. if (tmp * tmp != x) f = 0;
  10. }
  11. cout << (!f ? "YES\n" : "NO\n");
  12. }

1514B. AND 0, Sum Big

题面解释了那么多,本质就是 qpow(n,k) % mod

  1. using ll = long long;
  2. const int mod = 1e9 + 7;
  3. ll qpow(ll a, ll b) {
  4. ll ans = 1;
  5. a %= mod;
  6. for (; b; b >>= 1, a = a * a % mod)
  7. if (b & 1) ans = ans * a % mod;
  8. return ans;
  9. }
  10. void solve() {
  11. ll n, k;
  12. cin >> n >> k;
  13. cout << qpow(n, k) << "\n";
  14. }

1514C. Product 1 Modulo N

题意:

现在,您得到Baby Ehab的第一句话:“给定整数n,找到乘积为1模n的最长子序列 Codeforces Round #716 (Div. 2) A ~ D 个人题解 - 图3。” 请解决问题。
如果可以通过删除某些(可能是全部)元素从a获得b,则序列b是数组a的子序列。 空子序列的乘积等于1。

思路:

首先想到 Codeforces Round #716 (Div. 2) A ~ D 个人题解 - 图4 时,仅有一种情况就是 Codeforces Round #716 (Div. 2) A ~ D 个人题解 - 图5

然后在考虑 Codeforces Round #716 (Div. 2) A ~ D 个人题解 - 图6 时,维护 Codeforces Round #716 (Div. 2) A ~ D 个人题解 - 图7 。如果 Codeforces Round #716 (Div. 2) A ~ D 个人题解 - 图8Codeforces Round #716 (Div. 2) A ~ D 个人题解 - 图9 互质则可以加入序列。

最后如果 Codeforces Round #716 (Div. 2) A ~ D 个人题解 - 图10 最后一个数肯定不符合需要删去

  1. int n;
  2. void solve() {
  3. cin >> n;
  4. if (n == 2) {
  5. cout << "1\n1";
  6. return;
  7. }
  8. ll ans = 1;
  9. vector<int> v;
  10. for (int i = 1; i <= n; ++i) {
  11. if (__gcd(n, i) == 1) {
  12. v.push_back(i);
  13. ans = ans * i % n;
  14. }
  15. }
  16. if (ans == n - 1) v.pop_back();
  17. cout << v.size() << "\n";
  18. for (int x : v) cout << x << " ";
  19. }

1514D. Cut and Stick

涉及区间修改查询问题肯定是线段树(树状数组)了

  1. #include <bits/stdc++.h>
  2. using namespace std;
  3. using LL = long long;
  4. constexpr LL mod = 1000000007;
  5. constexpr int maxn = 300000 + 1;
  6. struct Node {
  7. int cur, cnt;
  8. Node operator*(const Node &p) const {
  9. if (cur == p.cur) return {cur, cnt + p.cnt};
  10. if (cnt >= p.cnt) return {cur, cnt - p.cnt};
  11. return {p.cur, p.cnt - cnt};
  12. }
  13. } t[maxn << 2];
  14. int a[maxn];
  15. vector<int> p[maxn];
  16. #define ls (v << 1)
  17. #define rs (ls | 1)
  18. #define tm ((tl + tr) >> 1)
  19. void build(int v, int tl, int tr) {
  20. if (tl == tr)
  21. t[v] = {a[tm], 1};
  22. if (tl < tr) {
  23. build(ls, tl, tm);
  24. build(rs, tm + 1, tr);
  25. t[v] = t[ls] * t[rs];
  26. }
  27. }
  28. Node query(int v, int tl, int tr, int L, int R) {
  29. if (tl >= L and tr <= R) return t[v];
  30. Node res = {0, 0};
  31. if (L <= tm) res = res * query(ls, tl, tm, L, R);
  32. if (R > tm) res = res * query(rs, tm + 1, tr, L, R);
  33. return res;
  34. }
  35. int main() {
  36. ios::sync_with_stdio(false);
  37. cin.tie(nullptr);
  38. int n, q;
  39. cin >> n >> q;
  40. for (int i = 1; i <= n; i += 1) cin >> a[i];
  41. for (int i = 1; i <= n; i += 1) p[a[i]].push_back(i);
  42. build(1, 1, n);
  43. for (int i = 1; i <= q; i += 1) {
  44. int L, R;
  45. cin >> L >> R;
  46. auto v = query(1, 1, n, L, R);
  47. int x = R - L + 1;
  48. int y = v.cur;
  49. int z = upper_bound(p[y].begin(), p[y].end(), R) - lower_bound(p[y].begin(), p[y].end(), L);
  50. cout << max(2 * z - x, 1) << "\n";
  51. }
  52. return 0;
  53. }