CF1661 Educational Codeforces Round 126 (Rated for Div. 2) 题解
感觉,越来越拉胯了,有点难过,明天希望可以好好学习,好好准备考研!八成新的自己我来力!
A Array Balancing
很明显的签到题,要求两个数组各自的相邻项差的绝对值最小,设\(mn=\min(a_i,b_i),mx=\max(a_i,b_i)\),把\(mn\)丢到在\(a[i]\),\(mx\)丢到\(b[i]\)即可。唔 和题解的解法不一样(
namo 这不素重点!重点是,为什么这个方法会ac呢?
假设我们已经按照上述方法构造出两组数列,保证了\(\forall i,a_i<b_i\)。

现在,我们把\(b_i\)和\(a_i\)调换位置,那么显然,\(|a_{i-1}-b_i|+|a_{i+1}-b_i|+|b_{i-1}-a_i|+|b_{i+1}-a_i| > |a_{i-1}-a_i|+|a_{i+1}-a_i|+|b_{i-1}-b_i|+|b_{i+1}-b_i|\)。
(前者让更大的数减去了更小的数)
AC代码:
int n;
const int N = 30 + 5;
int a[N], b[N];
void solve(){
scanf("%d", &n);
int tmp = 0; ll sm = 0;
for (int i=1;i<=n;++i){
scanf("%d", &a[i]);
}
for (int i=1;i<=n;++i){
scanf("%d", &b[i]);
tmp = min(a[i], b[i]);
a[i] = a[i] + b[i] - tmp, b[i] = tmp;
}
for (int i=1;i<n;++i){
sm = sm + abs(a[i] - a[i + 1]);
sm = sm + abs(b[i] - b[i + 1]);
}
printf("%lld\n", sm);
}
B Getting Zero
完全没想到BFS(),写完看到friends都在bfs我都惊惹
嗯……我们可以发现一个非常特别的事情,就是模数\(32768=2^{15}\),那么,任何值都可以通过\(\times2\)操作15次来到达0。因为,\(n\times 2^{15} \equiv 0(\bmod 2^{15})\)嘛。那么这件事就很好办乐,而我就这样直接选了无脑\(2^{15}\times 15\)的暴力,令人感叹()
时间复杂度:\(O(M\times 15)\)
int n;
const int N = 4e4 + 5, M = 32768;
int a[N], r[N];
void init(){
memset(r, 0x3f, sizeof(r));
r[0] = 0, r[M] = 0;
for (int i=1;i<M;++i){
int t = 0, cur = i;
while (cur % M != 0){
cur <<= 1;
++t;
}
r[i] = t;
}
for (int i=M-1;i>0;--i){
for (int j=1;j<=15;++j){
r[i] = min(r[i], r[(i + j) % M] + j);
}
}
}
int main(void){
init();
scanf("%d", &n);
for (int i=1;i<=n;++i){
scanf("%d", &a[i]);
printf(i==n?"%d\n":"%d ", r[a[i]]);
}
return 0;
}
C Water the Trees
给树浇水这题,首先要明确一点,就是,1和2这两个数它们其实是可以组成任何数的对吧?并且\(1+1=2\),也就是2可以用两个1代替。假设\(mx=\max\{a[n]\}\),其实我们这样就可以明了,浇水到最后树的高度一定都是\(mx\),或者都是\(mx+1\)。因为,要让所有树都达到某一高度\(h\),且\(h>mx+1\)的话,我们总能让树们先统一的到达\(mx\)或者\(mx+1\)的高度。
解决了第一个问题,我们要再用聪明的脑瓜子想到(以计算所有树到达\(mx\)为例),这就代表,对于第\(i\)棵树,它的高度是\(h_i\),那么它需要长大\(r_i=mx-h_i\)那么多。
- 假如\(r_i\)为奇数,那么显然,一定要有个1分给它。
- 如果\(r_i\)是偶数,我们可以一直在偶数天浇水,也可以让\(1+1=2\),凑出偶数。
OK!那现在怎么算最小天数已经呼之欲出辣,我们先算出\(r_i\)为奇数的个数,我们必须要分给它们一个1,这是我们必定要花的奇数天。奇数-1=偶数,剩下的就可以全部按照偶数计算。这只是一个小小的边界,俺相信剩下的内容大家都会惹。具体步骤可以参见代码(不许吐槽我一模一样的代码粘贴两遍QAQ,我高兴!嘴硬ing)
时间复杂度:\(O(N)\)
AC代码:
int n;
const int N = 3e5 + 5;
ll h[N];
void solve(){
scanf("%d", &n);
ll mx, one, two, day;
ll res = 2e18 + 1LL;
for (int i=1;i<=n;++i){
scanf("%lld", &h[i]);
}
sort(h + 1, h + 1 + n);
mx = h[n], one = 0, two = 0;
for (int i=1;i<=n;++i){
ll t = mx - h[i];
if (t & 1){
++one, two += (t - 1);
}
else two += t;
}
day = max(0LL, one - 1);
if (day * 2 >= two){
res = min(res, day + one);
}
else{
two -= one * 2, day = one * 2;
if (two % 3 == 0) day += two / 3 * 2;
else if (two % 3 == 1) day += two / 3 * 2 + 1;
else day += (two + 2) / 3 * 2;
res = min(res, day);
}
mx = h[n] + 1, one = 0, two = 0;
for (int i=1;i<=n;++i){
ll t = mx - h[i];
if (t & 1){
++one, two += (t - 1);
}
else two += t;
}
day = max(0LL, one - 1);
if (day * 2 >= two){
res = min(res, day + one);
}
else{
two -= one * 2, day = one * 2;
if (two % 3 == 0) day += two / 3 * 2;
else if (two % 3 == 1) day += two / 3 * 2 + 1;
else day += (two + 2) / 3 * 2;
res = min(res, day);
}
printf("%lld\n", res);
}
D Progressions Covering
好险,差点就屈服写线段树乐()
显然,我们要做一个贪心,从后往前取,把等差数列们逆向构造出来,这样代码的复杂度是\(O(N^2)\),显然是会\(TLE\)的(哼哼,我就是直接写然后TLE了的猪鼻)
贴一下\(O(N^2)\)的代码:
int main(void){
n = read(), m = read();
ll res = 0, cur = 0, inx = 0;
for (int i=1;i<=n;++i){
b[i] = read();
}
for (int i=n;i>=1;--i){
b[i] -= d[i];
if (b[i] <= 0) continue;
inx = (i >= m) ? m : i;
cur = (b[i] + inx - 1) / inx;
for (int j=1;j<inx&&i-j>0;++j){
d[i - j] += cur * (inx - j);
}
res += cur;
}
printf("%lld\n", res);
return 0;
}
那么,还有什么方法呢?也许我们可以直接考虑一个等差数列什么时候出现,以及什么时候消失?显然,如果\(b[i]>0\)时,我们就不得不构造一个等差数列来消除\(b[i]\)了,而在\(i-inx\)的那个位置,魔法消失了,\(b[i-inx]\)不需要再得到在\(i\)构造的等差数列的贡献了。
嗯……总之,对于这题,我们其实可以把他们看做若干个等差数列合并的情况,最后的那个尾项逐渐衰减,每次衰减公差之和,再用另一个数组\(r[n]\),记录每个等差数列能控制的最远的地方,那么这题也就结束了。
时间复杂度:\(O(N)\)
int n, m;
const int N = 3e5 + 5;
ll b[N], r[N];
ll read(){
ll x = 0, f = 1; char ch;
do{ch=getchar();if(ch=='-') f=-1;}while (ch<'0' || ch>'9');
do{x=x*10+ch-48;ch=getchar();}while (ch>='0' && ch<='9');
return x * f;
}
int main(void){
n = read(), m = read();
ll res = 0, cur = 0, inx = 0, all = 0, d = 0;
for (int i=1;i<=n;++i){
b[i] = read();
}
for (int i=n;i>=1;--i){
all -= d; // 去掉当前公差
d -= r[i]; // 去掉用完的公差
b[i] -= all;
if (b[i] <= 0) continue;
inx = (i >= m) ? m : i;
cur = (b[i] + inx - 1) / inx;
r[i - inx] += cur;
all += cur * inx;
d += cur;
res += cur;
}
printf("%lld\n", res);
return 0;
}
总体来说,这个教育场不是太难?方法都比较巧妙,但是边界也要稍微想下。wwww现在才写这玩意的题解,应该没人看吧
不过我才不在意会不会有人看呢()
CF1661 Educational Codeforces Round 126 (Rated for Div. 2) 题解的更多相关文章
- Educational Codeforces Round 63 (Rated for Div. 2) 题解
Educational Codeforces Round 63 (Rated for Div. 2)题解 题目链接 A. Reverse a Substring 给出一个字符串,现在可以对这个字符串进 ...
- Educational Codeforces Round 65 (Rated for Div. 2)题解
Educational Codeforces Round 65 (Rated for Div. 2)题解 题目链接 A. Telephone Number 水题,代码如下: Code #include ...
- Educational Codeforces Round 64 (Rated for Div. 2)题解
Educational Codeforces Round 64 (Rated for Div. 2)题解 题目链接 A. Inscribed Figures 水题,但是坑了很多人.需要注意以下就是正方 ...
- Educational Codeforces Round 60 (Rated for Div. 2) 题解
Educational Codeforces Round 60 (Rated for Div. 2) 题目链接:https://codeforces.com/contest/1117 A. Best ...
- Educational Codeforces Round 58 (Rated for Div. 2) 题解
Educational Codeforces Round 58 (Rated for Div. 2) 题目总链接:https://codeforces.com/contest/1101 A. Min ...
- Educational Codeforces Round 47 (Rated for Div. 2) 题解
题目链接:http://codeforces.com/contest/1009 A. Game Shopping 题目: 题意:有n件物品,你又m个钱包,每件物品的价格为ai,每个钱包里的前为bi.你 ...
- Educational Codeforces Round 93 (Rated for Div. 2)题解
A. Bad Triangle 题目:https://codeforces.com/contest/1398/problem/A 题解:一道计算几何题,只要观察数组的第1,2,n个,判断他们能否构成三 ...
- Educational Codeforces Round 33 (Rated for Div. 2) 题解
A.每个状态只有一种后续转移,判断每次转移是否都合法即可. #include <iostream> #include <cstdio> using namespace std; ...
- Educational Codeforces Round 78 (Rated for Div. 2) 题解
Shuffle Hashing A and B Berry Jam Segment Tree Tests for problem D Cards Shuffle Hashing \[ Time Lim ...
- Educational Codeforces Round 81 (Rated for Div. 2) 题解
过了n天补的题解:D AB就不用说了 C. Obtain The String 思路挺简单的,就是贪心,但是直接贪心的复杂度是O(|s|*|t|),会超时,所以需要用到序列自动机 虽然名字很高端但是就 ...
随机推荐
- TCP和KCP协议
TCP协议 KCP是一个快速可靠协议,能以比 TCP 浪费 10%-20% 的带宽的代价,换取平均延迟降低 30%-40%,且最大延迟降低三倍的传输效果.纯算法实现,并不负责底层协议(如UDP)的收发 ...
- 如何使用ventoy安装操作系统
使用ventoy安装操作系统 vrntoy简介 简单来说,Ventoy是一个制作可启动U盘的开源工具. 有了Ventoy你就无需反复地格式化U盘,你只需要把 ISO/WIM/IMG/VHD(x)/EF ...
- SQL提高查询性能的几种方式
创建索引,提高性能 索引可以极大地提高查询性能,其背后的原理: 索引是的数据库引擎能够快速的找到表中的数据,它们类似于书籍的目录,使得你不需要逐页查找所需要的信息 索引能够帮助数据库引擎直接定位到所需 ...
- 10、SpringMVC之处理Ajax请求
创建名为spring_mvc_ajax的新module,过程参考9.1节和9.5节 10.1.SpringMVC处理Ajax请求 10.1.1.页面请求示例 <input type=" ...
- 【Uni-App】API笔记 P1
1.调试打印: console.log() 向控制台打印 log 日志 console.debug() 向控制台打印 debug 日志 注:App 端自定义组件模式下,debug 方法等同于 log ...
- 【FastDFS】环境搭建 01 跟踪器和存储节点
FastDFS:分布式文件系统 它对文件进行管理,功能包括:文件存储.文件同步.文件访问(文件上传.文件下载)等,解决了大容量存储和负载均衡的问题. 特别适合以文件为载体的在线服务,如相册网站.视频网 ...
- 如何在Windows10电脑上打开3D建模STL文件
相关: https://www.bilibili.com/video/BV1gD4y1h7tj/
- 国产崛起,Solon:我们的性能是 Spring 的 300%
Solon 应用开发框架(java framework).是从零开始构建,有自主的标准规范与开放生态.纯血国产. 追求: 更快.更小.更简单 提倡: 克制.简洁.高效.开放.生态 相对于 Spring ...
- cubeide汉化包地址
http://mirrors.ustc.edu.cn/eclipse/technology/babel/update-site 具体步骤看洋桃物联网入门30步的视频
- windows权限维持汇总
Windows 权限维持 一.文件层面 1)attrib 使用 Attrib +s +a +h +r 命令 s:设置系统属性(System) a:设置存档属性(Archive) h:设置隐藏属性(Hi ...