首页 > 其他分享 >牛客暑假多校 2023 第一场

牛客暑假多校 2023 第一场

时间:2023-07-20 10:48:07浏览次数:37  
标签:ch int 多校 kN 牛客 端点 2023 include getchar

目录

写在前面

比赛地址:https://ac.nowcoder.com/acm/contest/57355

官方题解写得太好了都感觉没有自己整理的必要。

简单写写有启发性的东西。

我是垃圾。

L

发现进行三次操作后有:

\[(x, y, z)\rightarrow (a_{b_{c_x}}, b_{c_{a_{y}}}, c_{a_{b_{z}}}) \]

每个位置仅与三次操作前该位置上的数有关,则显然对于每个位置均存在操作次数为 3 的倍数的循环节。求出每个位置上目标状态在循环节上是第几个的,问题变为解线性同余方程组。

    //
/*
By:Luckyblock
*/
#include <cmath>
#include <cstdio>
#include <cctype>
#include <cstring>
#include <algorithm>
#define LL long long
const int kN = 1e5 + 10;
//=============================================================
int n, a[kN], b[kN], c[kN];
int lth[3][3], pos[3][3][kN], p[3];
//=============================================================
inline int read() {
  int f = 1, w = 0; char ch = getchar();
  for (; !isdigit(ch); ch = getchar()) if (ch == '-') f = -1;
  for (; isdigit(ch); ch = getchar()) w = (w << 3) + (w << 1) + (ch ^ '0'); 
  return f * w;
}
void Init() {
  int now[3] = {1, 1, 1}, ne[3];
  for (int i = 0; i < 3; ++ i) {
    for (int j = 0; j < 3; ++ j) {
      for (int k = 1; k <= n; ++ k) {
        pos[i][j][k] = -1;
      }
    }
  }

  for (int l = 0, i = l % 3; l <= 3 * n; ++ l, i = l % 3) {
    for (int j = 0; j < 3; ++ j) {
      if (pos[i][j][now[j]] == -1) {
        pos[i][j][now[j]] = lth[i][j]; 
        ++ lth[i][j];
      }
    }
    ne[0] = a[now[1]]; 
    ne[1] = b[now[2]];
    ne[2] = c[now[0]]; 
    for (int j = 0; j < 3; ++ j) now[j] = ne[j];
  }
}
LL exgcd(LL a_, LL b_, LL &x_, LL &y_) {
  if (!b_) {
    x_ = 1, y_ = 0;
    return a_;
  }
  LL d = exgcd(b_, a_ % b_, x_, y_);
  LL temp = x_;
  x_ = y_, y_ = temp - a_ / b_ * y_;
  return d;
}
LL lcm(LL x_, LL y_) {
  LL xx, yy, g = exgcd(x_, y_, xx, yy);
  return x_ / g * y_;
}
LL Solve(int i_) {
  LL M = lth[i_][0], ans = p[0];
  for (int j = 1; j < 3; ++ j) {
    LL A = M, B = lth[i_][j], C = (p[j] - ans % B + B) % B, x, y;
    LL g = exgcd(A, B, x, y);
    if (C % g) return -1;

    x = x * C / g % B, ans += x * M;
    M = lcm(M, B), ans = (ans % M + M) % M;
  }
  return ans;
}
//=============================================================
int main() {
  // freopen("1.txt", "r", stdin);

  n = read();
  for (int i = 1; i <= n; ++ i) a[i] = read();
  for (int i = 1; i <= n; ++ i) b[i] = read();
  for (int i = 1; i <= n; ++ i) c[i] = read();
  Init();
  int q = read();
  while (q --) {
    int key[3] = {}, flag1 = 1;
    for (int i = 0; i < 3; ++ i) key[i] = read();
    for (int i = 0; i < 3; ++ i) {
      int flag2 = 0;
      for (int j = 0; j < 3; ++ j) {
        p[j] = pos[i][j][key[j]];
        if (p[j] == -1) {
          flag2 = 1;
          break;
        }
      }
      if (flag2) continue;
      LL ret = Solve(i);
      if (ret != -1) {
        flag1 = 0;
        printf("%lld\n", 3ll * ret + i);
        break;
      }
    }
    if (flag1) printf("-1\n");
  }
  return 0;
}

H

将一组 \((a, b)\) 看做整体,可以发现它们在原数列中的位置关系是完全没有影响的,于是仅需着眼于 \((a, b)\) 中值的大小关系即可。

早注意到这个性质了但是没太在意,场上一直想着顺序对逆序对、、、钻牛角尖了、、、

于是考虑一对 \((a, b)\) 和 \((c, d)\) 在什么情况下交换才会产生贡献。大力手玩可以发现当且仅当 \(a<b\land c > d\) 或者 \(a>b\land c<d\) 时会产生贡献,贡献为区间 \([a, b] \cap [c,d]\) 的长度乘 2。

于是将所有 \((a, b)\) 按 \(a-b\) 的大小关系分类,对于每一类都在另一类中找与之区间交最大的即可。

实现时可以考虑对于待查找的区间 \([a, b]\),找到左端点小于 \(a\) 的右端点最大的区间。可以对另一类区间按照左端点升序右端点降序排序后,枚举过程中维护最大的右端点;也可以像我这样先对另一类的区间建树状数组再查询前缀最大值。

//
/*
By:Luckyblock
*/
#include <cmath>
#include <cstdio>
#include <cctype>
#include <cstring>
#include <algorithm>
#define LL long long
const int kN = 3e6 + 10;
//=============================================================
int n, a[kN], b[kN];
int datanum, data[kN];
LL start, ans;
//=============================================================
inline int read() {
  int f = 1, w = 0; char ch = getchar();
  for (; !isdigit(ch); ch = getchar()) if (ch == '-') f = -1;
  for (; isdigit(ch); ch = getchar()) w = (w << 3) + (w << 1) + (ch ^ '0'); 
  return f * w;
}
namespace Bit1 {
  #define lowbit(x) ((x)&(-x))
  const int kNode = kN;
  int f[kN], lim;
  void Init(int lim_) {
    lim = lim_;
    for (int i = 1; i <= lim; ++ i) f[i] = 0;
  }
  void Insert(int pos_, int val_) {
    for (int i = pos_; i <= lim; i += lowbit(i)) {
      f[i] = std::max(f[i], val_);
    }
  }
  int Query(int pos_) {
    int ret = 0;
    for (int i = pos_; i; i -= lowbit(i)) ret= std::max(ret, f[i]);
    return ret;
  }
  #undef lowbit
}
void Init() {
  n = read();
  for (int i = 1; i <= n; ++ i) a[i] = read();
  for (int i = 1; i <= n; ++ i) {
    b[i] = read();
    start += 1ll * abs(b[i] - a[i]);
  }
  ans = start;

  for (int i = 1; i <= n; ++ i) data[++ datanum] = a[i];
  for (int i = 1; i <= n; ++ i) data[++ datanum] = b[i];
  std::sort(data + 1, data + 2 * n + 1);
  datanum = 0;
  for (int i = 1; i <= 2 * n; ++ i) {
    if (data[i] != data[i - 1]) data[++ datanum] = data[i];
  }
  for (int i = 1; i <= n; ++ i) {
    a[i] = std::lower_bound(data + 1, data + datanum + 1, a[i]) - data;
    b[i] = std::lower_bound(data + 1, data + datanum + 1, b[i]) - data;
  }
}
//=============================================================
int main() {
  // freopen("1.txt", "r", stdin);
  Init();
  Bit1::Init(2 * n);
  for (int i = 1; i <= n; ++ i) {
    if (b[i] < a[i]) continue;
    Bit1::Insert(a[i], b[i]);
  }
  for (int i = 1; i <= n; ++ i) {
    if (b[i] > a[i]) continue;
    int maxr = Bit1::Query(b[i]);
    if (maxr == 0) continue;
    LL l = data[b[i]], r = std::min(data[a[i]], data[maxr]);
    ans = std::min(ans, start - 2ll * (r - l));
  }

  Bit1::Init(2 * n);
  for (int i = 1; i <= n; ++ i) {
    if (b[i] > a[i]) continue;
    Bit1::Insert(b[i], a[i]);
  }
  for (int i = 1; i <= n; ++ i) {
    if (b[i] < a[i]) continue;
    int maxr = Bit1::Query(a[i]);
    if (maxr == 0) continue;
    LL l = data[a[i]], r = std::min(data[b[i]], data[maxr]);
    ans = std::min(ans, start - 2ll * (r - l));
  }
  printf("%lld\n", ans);
  return 0;
}

标签:ch,int,多校,kN,牛客,端点,2023,include,getchar
From: https://www.cnblogs.com/luckyblock/p/17567667.html

相关文章

  • Java开发工具MyEclipse发布v2023.1.2,今年第二个修复版!
    MyEclipse一次性提供了巨量的Eclipse插件库,无需学习任何新的开发语言和工具,便可在一体化的IDE下进行JavaEE、Web和PhoneGap移动应用的开发;强大的智能代码补齐功能,让企业开发化繁为简。MyEclipsev2023.1.2官方正式版下载更新日志如下:v2023.1.2是MyEclipse2023的一个小错误修......
  • 【2023.07.20】成为渣男
    在约会了那么多女生后,我的内心逐渐趋向于平静,内心也不再痛苦了我对现在的女生是很失望的,好像每个人都是享乐主义我不是说享乐主义不好,但是她们给我的感受就是“这世上只有玩才是最重要的,抛弃了一切的责任和义务,只顾着自己开心就好”为什么失业了可以心安理得的啃老,为什么在花......
  • HDU 暑假多校 2023 第一场
    目录写在前面72837279727672757284写在最后写在前面补题地址:HDUOJ题库第63页,题号7275~7286。以下题号以题库中题号为准。题目选补,按照个人认为题目难度排序,因为我是菜狗。打这场看到马娘题目直接整个人兴奋,于是推了3h推不出来滚粗了。以为是手玩题没想到是正统博弈论呃......
  • SSO2.0 28-20230719
                      ......
  • 2023.7.19
    今天忙着做学校的实习报告和结束企业的实习任务,网安的东西晚上回来才看了一点。目前进度到了ret2dlresolvePartialRELRO的stage4(ctfwiki上的进度),之前发现那几个阶段大部分步骤都是类似的,所以在刚开始几个阶段把那几个东西(如栈迁移的第一步payload构建、第二步payload构建)弄懂......
  • 【专题】2023中国品牌消费趋势洞察报告PDF合集分享(附原数据表)
    报告链接:https://tecdat.cn/?p=33262原文出处:拓端数据部落公众号品牌是企业乃至国家竞争力的综合体现。在2016年6月20日,国务院办公厅发布了《关于发挥品牌引领作用推动供富结构升级的意见》,首次提出了设立“中国品牌日”的建议。站在时代变革的风口,中国品牌抓住了创新发展的机......
  • 2023.7.19
    早上起来,零零碎碎的就是雨声,起来收了衣服就看起了书,说实话,在雨天的家里点灯看书真的有那味了,感觉整个人都升华了,中午炒了鱼香肉丝,手艺不行了,酸得离谱,糖也方少了,下午写了会儿代码,晚上就休息了。......
  • 2023.7.19
    今天上午吃到了奶奶包的三鲜包子,很好吃!上午给男朋友发消息但是他的电脑被借去投屏演示了,直接社死一波(报意思呜呜)下午和好朋友一起玩了一会游戏,一边玩一边吐槽破事,被人热暴力了谁懂,真的心梗犯了晚上许久不见的好友上线啦,还是一如既往的搞笑今天还去写了实验报告!明天准备去练......
  • 20230629-可持久化数据结构 1
    20230629权值线段树P3369【模板】普通平衡树题目大意传送门Solution可以用平衡树实现但用权值线段树代码量更少且速度更快注意前驱和后继的写法H_W_Y-Coding#include<bits/stdc++.h>usingnamespacestd;#definelb(x)lower_bound(b+1,b+cnt+1,x)-bconstintm......
  • 20230626-树链剖分+点分治
    20230626重链剖分计算每个节点子树大小,判断出每个点的重儿子优先遍历重儿子连边,并且按照DFS序重新编号特点:每条重链上的点编号是连续的每个点为根的子树内所有点的编号是连续的$\to$线段树需求:对于树上两点\(x,y\)路径上的所有点进行操作必然不能避免的事情......