Preface

又自己开了场CF/Atcoder杂题,比昨天的稍难,题目也更有趣了

昨晚炉石检验血统果然是非洲人...

希望这是给NOIP2018续点rp吧

A.CF1068C-Colored Rooks

现在还没理解题意...

B. CF1070K-VideoPosts

一道模拟,没什么好说的.

不过一开始还是WA了...一个智障的坑,感觉做题还是不细心

const int maxn=100005;
const int inf=0x7fffffff;
int a[maxn],ave,n,k,cnt=0;
int ans[maxn],tot=0;
ll sum=0;
int main(){
read(n),read(k);
for(ri i=1;i<=n;i++){
read(a[i]);
sum+=a[i];
}
if(sum%k!=0){
puts("No");
return 0;
}
ave=sum/k;
sum=0;
for(ri i=1;i<=n;i++){
sum+=a[i],cnt++;
if(sum==ave){
ans[++tot]=cnt;//printf("%d ",cnt);
sum=cnt=0;
}
else if(sum>ave){
puts("No");
return 0;
}
}
puts("Yes");
for(ri i=1;i<=tot;i++)printf("%d ",ans[i]);
puts("");
return 0;
}

C. CF1036D-VasyaAndArrays

一看就是一道贪心题,很多人都会猜测就是两个指针不断拓展,如果两个数相等就不加.

想了想发现似乎是正确的,但是不会严格证明,交了发居然A了

const int maxn=300005;
const int inf=0x7fffffff;
int n,m;
int a[maxn],b[maxn];
ll sum1=0,sum2=0;
int main(){
read(n);
for(ri i=1;i<=n;i++)read(a[i]),sum1+=a[i];
read(m);
for(ri i=1;i<=m;i++)read(b[i]),sum2+=b[i];
if(sum1!=sum2){
puts("-1");
return 0;
}
int len=0,pos1=1,pos2=1;
sum1=a[1],sum2=b[1];
while(1){
while(sum1!=sum2){
if(sum1>sum2)sum2+=b[++pos2];
else sum1+=a[++pos1];
}
len++;
if(pos1==n&&pos2==m)break;
sum1=a[++pos1],sum2=b[++pos2];
}
printf("%d\n",len);
return 0;
}

D. CF1038D-Slime

非常有意思的题,一开始想区间DP,但是发现好像是有后效性的,交了发果然WA了

然后只能往贪心这方面想

偶然发现样例非常有意思,一个全正数, 一个全负数+0.

易知如果全是正数的话就可以贪心,你用最小的史莱姆吃掉出最大值以外的所有数,然后最大值吃掉这个数肯定是最优的.这样子答案就是sum-mi-mi

如果是全负数加上一个0,我们就是用0吃掉所有负数显然是最优的

那如果既有非负数又有负数,我们可以用负数减去除最大值以外所有非负整数,然后最大值吃掉所有负数就是最优的,这样子就是所有元素之和

但是如果全都是负数按照全都是正数的思路就是sum-mx-mx

const int maxn=500005;
const int inf=1e9;
int n,a[maxn],mi=inf,mx=-inf;
int main(){
bool flag=0,flag_2=0;
ll sum=0;
read(n);
if(n==1){
read(a[1]);
printf("%d\n",a[1]);
return 0;
}
for(ri i=1;i<=n;i++){
read(a[i]);
mi=min(a[i],mi);
mx=max(a[i],mx);
sum+=abs(a[i]);
if(a[i]<0)flag=1;
if(a[i]>=0)flag_2=1;
}
if(flag){
if(flag_2)printf("%lld\n",sum);
else printf("%lld\n",sum+mx*2);
}
else {
printf("%lld\n",sum-mi*2);
}
return 0;
}

E. Atcoder4167-Equal Cut

一道ARC的B题就不会做了,太菜了...

感觉solution很妙啊,枚举中间的断点.这时候分成了L,R两部分,显然我们还要把L,R分成L1,L2和R1,R2两部分

这时候有一个结论就是让abs(L1-L2)和abs(R1-R2)尽量小一定是最优方案,这个还是比较显然的

这时候可以发现我们在枚举中间断点的时候分割L1,L2的断点和分割R1,R2的断点都是单调的

这里的断点是指abs(L1-L2)和abs(R1-R2)尽量小的断点

于是我们就可以\(O(N)\)扫一遍得出答案了

同时发现一个很坑的地方:

std::abs()而不是abs(),因为差点没查出错来

const int maxn=1000005;
const int inf=0x7fffff;
int n;
ll a[maxn];
ll sum[maxn],mi=1e18,mx=-1e18,ans=1e18,tmp;
int main(){
int x,y;
read(n);
sum[0]=0;
for(ri i=1;i<=n;i++)read(a[i]),sum[i]=sum[i-1]+a[i];
int l=1,r=3;
for(ri k=2;k<=n-2;k++){
while((abs((sum[k]-sum[l+1])-(sum[l+1]))<abs(sum[k]-sum[l]-sum[l]))&&l+1<k)l++;
while((abs((sum[n]-sum[r+1])-(sum[r+1]-sum[k]))<abs((sum[n]-sum[r])-(sum[r]-sum[k])))&&r+1<n)r++;
mi=1e18,mx=-1e18;
tmp=sum[k]-sum[l];
mi=min(mi,tmp),mx=max(mx,tmp);
tmp=sum[l];
mi=min(mi,tmp),mx=max(mx,tmp);
tmp=sum[n]-sum[r];
mi=min(mi,tmp),mx=max(mx,tmp);
tmp=sum[r]-sum[k];
mi=min(mi,tmp),mx=max(mx,tmp);
ans=min(ans,mx-mi);
}
printf("%lld\n",ans);
return 0;
}

F. Atcoder4351-Median Of Medians

这题考试的时候也不会做,考试后发现正解简直太妙了

首先我们需要知道一个性质:如果\(x\)是一个长度为\(N\)的序列的中位数,那么小于等于x的数的个数至少有\(N/2+1\)个

于是我们不妨二分一下最后的中位数是哪个,然后我们只需要知道有多少个区间的中位数是小于等于我们二分的这个数就可以了

这里就需要一个高端操作:我们将原序列中小于等于这个数的数置为1,否则置为-1;这样操作之后可以发现如果一个区间的中位数小于等于x,那么这个区间之和肯定大于0.所以我们转化成有多少个区间之和大于0.

我们对这个新序列求一遍前缀和,我们都知道区间\([L,R]\)的和等于\(sum[R]-sum[L-1]\),如果想要这个区间和大于0,实际上就是\(sum[R]>sum[L-1]\),又由于\(R>L-1\),那么我们发现区间之和大于0的区间个数实际上就是新序列前缀和后的顺序对个数,我们离散化之后按照逆序对套路处理即可

但是注意这时候我们没有计算类似\([1,R]\)的区间,这个直接记录一下就好了

但是回到前面的话题,我们已经知道了有多少个区间的中位数小于等于当前二分的这个数,我们该如何更改这个二分边界呢?

还是一开始那个性质,由于区间个数总共有\(N \times (N+1)/2\)个,所以大于等于二分的这个数的区间个数如果大于等于\(N \times (N+1)/4+1\)的话,则将二分右边界左移,否则左边界右移

注意一开始\(N \times (N+1)\) 前没打1ll,结果爆int了,查了好久的错...

const int maxn=200005;
const int inf=0x7fffffff;
int n,nn,a[maxn],b[maxn],c[maxn],mx=-inf,mi=inf;
ll sum[maxn<<2];
inline void update(int x,int d){for(;x<=nn;x+=x&(-x))sum[x]+=d;}
inline ll query(int x){ll ans=0;for(;x;x-=x&(-x))ans+=sum[x];return ans;}
inline ll chk(int k){
ll ans=0;
b[0]=0;
for(ri i=1;i<=n;i++){
b[i]=b[i-1]+((a[i]<=k)?1:-1);
c[i]=b[i];
ans+=(b[i]>0);//记录[1,R]的区间
}
std::sort(c+1,c+1+n);
nn=std::unique(c+1,c+1+n)-(c+1);
memset(sum,0,sizeof(sum));
for(ri i=1;i<=n;i++){
b[i]=lower_bound(c+1,c+1+nn,b[i])-c;//离散化
ans+=query(b[i]-1);
update(b[i],1);
}
return ans;
}
int main(){
read(n);
for(ri i=1;i<=n;i++){
read(a[i]);
mi=min(mi,a[i]),mx=max(mx,a[i]);
}
int L=mi,R=mx,mid,ans;
ll lim=1ll*n*(n+1)/4+1;
while(L<=R){
mid=(L+R)>>1;
if(chk(mid)>=lim)ans=mid,R=mid-1;
else L=mid+1;
}
printf("%d\n",ans);
return 0;
}

Atcoder&CodeForces杂题11.7的更多相关文章

  1. Atcoder&CodeForces杂题11.6

    Preface NOIP前突然不知道做什么,感觉思维有点江僵化,就在vjudge上随便组了6道ABC D+CF Div2 C/D做,发现比赛质量还不错,知识点涉及广,难度有梯度,码量稍小,思维较多. ...

  2. Codeforces 杂题集 2.0

      记录一些没有写在其他随笔中的 Codeforces 杂题, 以 Problemset 题号排序   1326D2 - Prefix-Suffix Palindrome (Hard version) ...

  3. AtCoder,Codeforces做题记录

    AGC024(5.20) 总结:猜结论,“可行即最优” B: 给定一个n的排列,每次可以将一个数移到开头或结尾,求变成1,2,...,n所需的最小步数. 找到一个最长的i,i+1,...,j满足在排列 ...

  4. Codeforces Global Round 11 个人题解(B题)

    Codeforces Global Round 11 1427A. Avoiding Zero 题目链接:click here 待补 1427B. Chess Cheater 题目链接:click h ...

  5. 贪心/构造/DP 杂题选做Ⅲ

    颓!颓!颓!(bushi 前传: 贪心/构造/DP 杂题选做 贪心/构造/DP 杂题选做Ⅱ 51. CF758E Broken Tree 讲个笑话,这道题是 11.3 模拟赛的 T2,模拟赛里那道题的 ...

  6. 贪心/构造/DP 杂题选做Ⅱ

    由于换了台电脑,而我的贪心 & 构造能力依然很拉跨,所以决定再开一个坑( 前传: 贪心/构造/DP 杂题选做 u1s1 我预感还有Ⅲ(欸,这不是我在多项式Ⅱ中说过的原话吗) 24. P5912 ...

  7. Codeforces刷题计划

    Codeforces刷题计划 已完成:-- / -- [Codeforces370E]370E - Summer Reading:构造:(给定某些数,在空白处填数,要求不下降,并且相邻差值<=1 ...

  8. Codeforces Beta Round #11 B. Jumping Jack 数学

    B. Jumping Jack 题目连接: http://www.codeforces.com/contest/11/problem/B Description Jack is working on ...

  9. Codeforces Beta Round #11 A. Increasing Sequence 贪心

    A. Increasing Sequence 题目连接: http://www.codeforces.com/contest/11/problem/A Description A sequence a ...

随机推荐

  1. Maven Multi-Module Example

    Maven Multi-Module - 国内版 Binghttps://cn.bing.com/search?q=Maven+Multi-Module&qs=n&form=QBRE& ...

  2. Ionic4.x、Cordova Android 检测应用版本号、服务器下载文件以及实现App自动升级、安装

    Android App 升级执行流程 1.获取本地版本号 2.请求服务器获取服务器版本号 3.本地版本和服务器版本不一致提示升级,弹窗提示用户是否更新 4.用户确定升级,调用文件传输方法下载 apk ...

  3. openresty开发系列11--openresty的api入门

    openresty开发系列11--openresty的api入门 1)ngx_lua模块的hello world编辑nginx下conf配置文件nginx.conf# vi nginx.conf在se ...

  4. shell编程系列21--文本处理三剑客之awk中数组的用法及模拟生产环境数据统计

    shell编程系列21--文本处理三剑客之awk中数组的用法及模拟生产环境数据统计 shell中的数组的用法: shell数组中的下标是从0开始的 array=("Allen" & ...

  5. 导出swagger2生成的文档

    百度了好多篇用法,没法用.特此记录一下 一.下载项目 下载https://github.com/Swagger2Markup/spring-swagger2markup-demo下的项目,保存,注意文 ...

  6. osg gdal加载tif数据文件

    osg加载.tif地形数据文件 #ifdef _WIN32 #include <Windows.h> #endif // _WIN32 #include <iostream> ...

  7. Qt编写自定义控件64-垂直时间轴

    一.前言 垂直时间轴控件,主要用来描述企业发展历程大事件,或者软件版本迭代历史等,通过时间节点和事件描述来直观的展示发展的过程,一般在web网页或者app中经常看到此类控件,尤其是公司的官网关于公司部 ...

  8. c#中多线程同步Lock(锁)的研究以及跨线程UI的操作 (转)

    https://www.cnblogs.com/tommyheng/p/4104552.html 本文只针对C#中,多线程同步所用到的锁(lock)作为研究对象.由于想更直观的显示结果,所以,在做de ...

  9. LeetCode_258. Add Digits

    258. Add Digits Easy Given a non-negative integer num, repeatedly add all its digits until the resul ...

  10. FormsAuthentication使用指南

    配置安全鉴别 鉴别是指鉴定来访用户是否合法的过程.ASP.NET Framework支持三种鉴别类型: Windows鉴别: NET Passport鉴别: Forms鉴别. 对于某一特定的应用程序, ...