A ABC

水题0.0

B Roof Construction

构造题,经过实验构造出了0的右边是不超过\(n\)的最大的\(2^k\rightarrow n\),左边是\(2^k-1,2^k-2,..,1\)

明天起来看看B的证明。

可恶!出题人不写证明,那我也摸了

C Strange Test

给定两个整数\(a,b~(a<b)\),可以执行下列三种操作,每种操作都可以进行任意次:

  • \(a:=a+1\)
  • \(b:=b+1\)
  • \(a:=a|b\)

要求输出最少需要多少次操作,可以使得\(a,b\)相等?

数据范围:\(1\leq t \leq 10^4;1\leq a<b\leq 10^6;\sum b\leq 10^6\)

猜的结论,是要么\(a:=a+1\),然后进行按位或操作;要么一直\(b:=b+1\),然后最后只会进行最多一次按位或操作。所以求出来这两种方法得到的答案,然后比较一下即可。

int x, y;
const int INF = 0x3f3f3f3f; void solve(){
scanf("%d%d", &x, &y);
int r1 = 0, r2 = 0, res = y - x;
int a = x, b = y;
while ((a|b) != b && r1 <= res){
++a, ++r1;
}
if (a != b) ++r1;
a = x, b = y;
while ((a|b) != b && r2 <= res){
++b, ++r2;
}
if (a != b) ++r2;
res = min({res, r1, r2});
printf("%d\n", res);
}

正解当然不应该这么做!具体怎么做的明天再看。

首先,第三种操作最多用一次。因为,它不会减少\(a\),并且在操作后一定有\(b\leq a\)。这意味着,在进行操作3后,我们最多只能进行若干次操作2了。

  • 如果我们不使用第三种操作,那么答案为\(b-a\)。

  • 如果我们先使用了若干次操作1和操作2,然后使用了一次操作3,最后又使用了若干次操作2。

    假设经过这些操作后,\(a\rightarrow a',b\rightarrow b'(a\leq a',b\leq b')\)。

    此时花费的操作数为\((a'-a)+(b'-b)+1+((a'|b')-b')=a'+(a'|b')+(1-a-b)\)。

为了找到最优的答案,我们可以迭代\(a'\),令\(a'=a:b\),对于固定的\(a'\),我们要做的就是最小化\(a'|b'\),设\(b'\)初始值为0,然后从最高位到最低位迭代,有如下四种情况:

  • 当前位\(a'=0,b=1\),那么当前位\(b'\)填1;
  • 当前位\(a'=0,b=0\),那么当前位\(b'\)填0;
  • 当前位\(a'=1,b=1\),那么当前位\(b'\)填1;
  • 当前位\(a'=1,b=0\),那么当前位\(b'\)填1,终止迭代。

时间复杂度\(O(b\log b)\)或者\(O(b)\)。(第二种情况直接使用位运算把\(O(\log b)\rightarrow O(1)\)。)

嗯,这样就是最优的没有问题!

题目的Bonus:证明最优情况一定为\(a'=a\),或者\(b'=b\)。(也就是猜的结论)

int a, b;

void solve(){
scanf("%d%d", &a, &b);
int mn = b - a;
for (int ax=a;ax<=b;++ax){
int bx = 0, cur;
for (int i=20;i>=0;--i){
if (b >> i & 1){
bx += (1 << i);
}
else if (ax >> i & 1){
bx += (1 << i);
break;
}
}
cur = ax + (ax | bx) - a - b + 1;
mn = min(mn, cur);
}
printf("%d\n", mn);
}

D New Year Concert

有一个数组\(a[n]\),令\(a[n]\)的长度为\(k\)的前缀子序列\(b[k]=\{a_1,a_2,..,a_{k}\}\),如果其中有任何一个连续区间满足\(1\leq l\leq r\leq k,\gcd(b_l,b_{l+1},..,b_{r})=r-l+1\),那么就称这个序列是boring的。

为了避免\(b[k]\)boring,可以进行以下操作若干次,将\(b[k]\)中的一个元素\(b_t\)用\(d\)替换,即\(b_t=d\)。注意,每次操作的\(d,t\)都可以是不同的。定义\(f(b)\)为令数组\(b\)不再boring的最小操作次数,对于所有\(a[n]\)的前缀,求\(f([a_1]),f([a_1,a_2]),..,f([a_1,a_2,..,a_n])\)。

数据范围:\(1\leq n \leq 2\times 10^5;1\leq a_i \leq 10^9\)

嗯……首先,对于固定的左端点\(l\),随着\(r\)的增大,\(gcd(a_l,..,a_r)\)一定是不递增的。那么就有了一个很重要的性质:固定左端点,满足\(gcd(a_l,..,a_r)=r+l-1\)的\(r\)仅有一个,假如满足条件的为\(r'\)。从这里也可以看出来,boring子序列的数量最多不超过\(n\)个。那么怎样就可以消除这个boring呢?答案是在\((a_l,a_{r'})\)中的任一个数中间,修改\(a_k=\)某一个很大的质数,这个大质数要满足后面没有数是它的倍数,这里不妨设这个大质数\(p=10^9+7\)。

如果我们令\(a_i=p\),那么所有包含\(i\)的区间,boring都会消失。这是一个标准的贪心问题:找到最小的\(r\),然后所有包含\(r\)的段不再boring,删除这些段,然后继续操作。

嗯……我看的题解思路差不多,就是固定\(r\),然后找\(l\),定义\(pos\)为上一个修改了\(a[pos]\)的右端点,然后循环到\(d\geq i-pos\)时停止,当\(d=i-pos\)时,那就修改当前的\(i\),则\(pos=i\)。当然,也可以使用二分找到这样的\(d\)。区间查询\(gcd\),使用线段树即可。

(题解写的代码什么玩意 看不懂QAQ)

int n;
const int N = 2e5 + 5;
int a[N];
struct node{
int le, ri, v;
};
node seg[N<<2]; int gcd(int a, int b){
return b ? gcd(b, a % b) : a;
} void pushup(int oo){
seg[oo].v = gcd(seg[ls].v, seg[rs].v);
} void build(int oo, int le, int ri){
seg[oo] = {le, ri, 0};
if (le >= ri){
seg[oo].v = a[le];
return ;
}
int mid = (le + ri) >> 1;
build(ls, le, mid);
build(rs, mid + 1, ri);
pushup(oo);
} int query(int oo, int x, int y){
int le = seg[oo].le, ri = seg[oo].ri;
if (le >= x && ri <= y){
return seg[oo].v;
}
int res = 0, mid = (le + ri) >> 1;
if (x <= mid){
res = gcd(res, query(ls, x, y));
}
if (y > mid){
res = gcd(res, query(rs, x, y));
}
return res;
} int main(void){
scanf("%d", &n);
for (int i=1;i<=n;++i){
scanf("%d", &a[i]);
}
build(1, 1, n);
int res = 0, pos = 0;
for (int i=1;i<=n;++i){
int d = query(1, pos + 1, i);
while (d < i - pos){
pos++;
d = query(1, pos + 1, i);
}
if (d == i - pos){
res++, pos = i;
}
printf(i==n?"%d\n":"%d ", res);
}
return 0;
}

E1&E2 Distance Tree(easy & hard version )

有一棵树,根节点为1,每条边的权值为1。定义\(d(v)\)为从结点1到结点\(v\)的距离。假设从结点\(a\)出发,向某个结点连\(b\)了一条长度为\(x\)的边,定义\(f(x)=\max\{d(v)|1\leq v\leq n\}\),要求输出\(f(x)\)的最小值,\(1\leq x\leq n\)。

数据范围:\(1\leq n \leq 3\times 10^5\)

首先,应该是从结点1向其他的某个结点连边。然后要求最长的路径最短,可以想到是二分。如果我们连边的话,假设从结点1向结点\(b\)连了一个长度为\(x\)的边,并假设此时所有的边都\(\leq mid\)。那么,所有的结点要么直接按照原来的树走到1,路径长度\(\leq mid\),要么就是通过新连的边到达1,新的路径长度\(\leq mid\)。那么对于\(mid\),我们只要检查所有的\(>mid\)的路径能否变成\(\leq mid\)的路径。

设\(rt\)为到结点1距离最远的结点,则\(f[i]\):和结点1的距离\(\geq i\)时,到结点\(rt\)的最大距离。显然,我们会找到一个原本路径\(\geq i\)的点集中,两点间的最长距离。连接这个最长路的中点\(u\)和结点1,则剩下的所有点的距离都会\(\leq x+\lceil \frac{dis[u][1]}{2} \rceil\)。而当\(x\)过大时,这条路径会变得还不如原本路径,因此要和\(dis[rt][1]\)取一个最小值。

int n, rt;
const int N = 3e5 + 5;
vector<int> ve[N];
int d[N][2], f[N];
// d[i][0]:到结点1的距离; d[i][1]:到结点rt的距离
// f[i]: 和结点1的距离为>=i时, 到结点rt的最大距离 void init(){
for (int i=0;i<=n;++i){
ve[i].clear();
f[i] = d[i][0] = d[i][1] = 0;
}
} void dfs(int u, int pre, int x){
if (pre) d[u][x] = d[pre][x] + 1;
for (auto to : ve[u]){
if (to == pre) continue;
dfs(to, u, x);
}
} bool check(int x, int v){
return x >= min(d[rt][0], v + (f[x + 1] + 1) / 2);
} void solve(){
n = read();
init();
int u, v;
for (int i=1;i<n;++i){
u = read(), v = read();
ve[u].push_back(v), ve[v].push_back(u);
}
dfs(1, 0, 0);
int mx = -1;
for (int i=1;i<=n;++i){
if (mx < d[i][0]){
mx = d[i][0], rt = i;
}
}
dfs(rt, 0, 1);
for (int i=1;i<=n;++i){
f[d[i][0]] = max(f[d[i][0]], d[i][1]);
}
for (int i=n-1;i>=0;--i){
f[i] = max(f[i], f[i + 1]);
} for (int i=1;i<=n;++i){
int L = 0, R = n, ans = n;
while (L <= R){
int mid = (L + R) >> 1;
if (check(mid, i)){
ans = mid;
R = mid - 1;
}
else L = mid + 1;
}
printf("%d ", ans);
}
puts("");
}

cf1632 Codeforces Round #769 (Div. 2)题解的更多相关文章

  1. Codeforces Round #182 (Div. 1)题解【ABCD】

    Codeforces Round #182 (Div. 1)题解 A题:Yaroslav and Sequence1 题意: 给你\(2*n+1\)个元素,你每次可以进行无数种操作,每次操作必须选择其 ...

  2. Codeforces Round #608 (Div. 2) 题解

    目录 Codeforces Round #608 (Div. 2) 题解 前言 A. Suits 题意 做法 程序 B. Blocks 题意 做法 程序 C. Shawarma Tent 题意 做法 ...

  3. Codeforces Round #525 (Div. 2)题解

    Codeforces Round #525 (Div. 2)题解 题解 CF1088A [Ehab and another construction problem] 依据题意枚举即可 # inclu ...

  4. Codeforces Round #528 (Div. 2)题解

    Codeforces Round #528 (Div. 2)题解 A. Right-Left Cipher 很明显这道题按题意逆序解码即可 Code: # include <bits/stdc+ ...

  5. Codeforces Round #466 (Div. 2) 题解940A 940B 940C 940D 940E 940F

    Codeforces Round #466 (Div. 2) 题解 A.Points on the line 题目大意: 给你一个数列,定义数列的权值为最大值减去最小值,问最少删除几个数,使得数列的权 ...

  6. Codeforces Round #677 (Div. 3) 题解

    Codeforces Round #677 (Div. 3) 题解 A. Boring Apartments 题目 题解 简单签到题,直接数,小于这个数的\(+10\). 代码 #include &l ...

  7. Codeforces Round #665 (Div. 2) 题解

    Codeforces Round #665 (Div. 2) 题解 写得有点晚了,估计都官方题解看完切掉了,没人看我的了qaq. 目录 Codeforces Round #665 (Div. 2) 题 ...

  8. Codeforces Round #160 (Div. 1) 题解【ABCD】

    Codeforces Round #160 (Div. 1) A - Maxim and Discounts 题意 给你n个折扣,m个物品,每个折扣都可以使用无限次,每次你使用第i个折扣的时候,你必须 ...

  9. Codeforces Round #383 (Div. 2) 题解【ABCDE】

    Codeforces Round #383 (Div. 2) A. Arpa's hard exam and Mehrdad's naive cheat 题意 求1378^n mod 10 题解 直接 ...

  10. Codeforces Round #271 (Div. 2)题解【ABCDEF】

    Codeforces Round #271 (Div. 2) A - Keyboard 题意 给你一个字符串,问你这个字符串在键盘的位置往左边挪一位,或者往右边挪一位字符,这个字符串是什么样子 题解 ...

随机推荐

  1. 【ElasticSearch】数据迁移方案

    一.需求背景 ES环境要从单机迁移到集群上面 现在已有的数据也要搬过去,有几个索引三四千万数据大概 二.实现方案 有两种,使用ElasticDump和LogStash的ES插件 1.ElasticDu ...

  2. 【Docker】08 部署挂载本地目录的MySQL

    拉取MySQL镜像: docker pull mysql:8.0.21 执行挂载运行MySQL容器的命令: docker run -dit \ --name mysql-test \ -p 3306: ...

  3. 作为国产深度学习框架中分布式计算特性最强大的OneFlow的最大缺点是什么?

    OneFlow是国产深度学习框架中分布式计算特性最强大的,因为其原生支持分布式特性,世界上的历史中的深度学习框架唯一可以做到这一点的也就只有Google的TensorFlow和Jax了,虽然有人说Go ...

  4. Ubuntu18.04环境下 以太坊Geth的安装

    ubuntu18.04系统下安装: sudo apt-get install software-properties-common sudo add-apt-repository -y ppa:eth ...

  5. 内网穿透之实践记录,使用花生壳进行内外穿透,场景:在家远程ssh连接到公司电脑或学校服务器

    今天在网上闲逛的时候看到这样一个内网穿透的软件,ngrok, https://gitee.com/kxwinxp/ngrok 记得10多年前自己在读大学的时候曾经好一段时间在研究内网穿透技术,最后发现 ...

  6. 高效调度新篇章:详解DolphinScheduler 3.2.0生产级集群搭建

    转载自tuoluzhe8521 导读:通过简化复杂的任务依赖关系, DolphinScheduler为数据工程师提供了强大的工作流程管理和调度能力.在3.2.0版本中,DolphinScheduler ...

  7. Apache DolphinScheduler 在奇富科技的首个调度异地部署实践

    奇富科技(原360数科)是人工智能驱动的信贷科技服务平台,致力于凭借智能服务.AI研究及应用.安全科技,赋能金融机构提质增效,助推普惠金融高质量发展,让更多人享受到安全便捷的金融科技服务.作为国内领先 ...

  8. Sentry 产品指南文档(附:详细脑图整理)

    Sentry 基础知识 https://docs.sentry.io/product/ https://docs.sentry.io/product/sentry-basics/ 问题 https:/ ...

  9. 一文搞懂Cortex-A9 ADC裸机和基于Linux驱动编写方法

    前言 在嵌入式开发中,ADC应用比较频繁,本文主要讲解ADC的基本原理以及如何编写基于ARM的裸机程序和基于Linux的驱动程序. ARM架构:Cortex-A9 Linux内核:3.14 在讲述AD ...

  10. Docker不同宿主机网络打通

    本方式使用docker Swarm集群的方式创建overlay 网络进行打通 背景 因java微服务使用nacos做配置中心,为了解决Nacos服务注册使用Docker容器内网ip问题,使用此方案 前 ...