点此进入比赛

\(T1\):Football(点此看题面

大致题意: 求\(max(20a_i-10b_i,0)\)。

送分题不解释。

#include<bits/stdc++.h>
#define Tp template<typename Ty>
#define Ts template<typename Ty,typename... Ar>
#define Reg register
#define RI Reg int
#define Con const
#define CI Con int&
#define I inline
#define W while
#define N 150
#define Gmax(x,y) (x<(y)&&(x=(y)))
using namespace std;
int n,a[N+5],b[N+5];
int main()
{
RI Tt,i,x,y,ans;scanf("%d",&Tt);W(Tt--)
{
for(scanf("%d",&n),ans=0,i=1;i<=n;++i) scanf("%d",a+i);
for(i=1;i<=n;++i) scanf("%d",b+i),Gmax(ans,20*a[i]-10*b[i]);//统计答案
printf("%d\n",ans);
}return 0;
}

\(T2\):Distribute Apples(点此看题面

大致题意: 有两种分苹果方法,一种把\(n\)个苹果平均分到\(k\)个盒子中,一种每次在一个盒子中放\(k\)个苹果放\(\frac nk\)次,判断两种放法结果是否一样。

考虑苹果总数是一样的,因此只要第二种方法能做到平均分配,结果就是一样的。

而第二种方法做到平均分配,就说明\(k|\frac nk\)。

判一下即可。

#include<bits/stdc++.h>
#define Tp template<typename Ty>
#define Ts template<typename Ty,typename... Ar>
#define Reg register
#define RI Reg int
#define Con const
#define CI Con int&
#define I inline
#define W while
#define N 150
#define Gmax(x,y) (x<(y)&&(x=(y)))
using namespace std;
long long n,k;
int main()
{
RI Tt,i,x,y,ans;scanf("%d",&Tt);W(Tt--)
scanf("%lld%lld",&n,&k),puts((n%k||(n/k)%k)?"YES":"NO");//判断k|(n/k)
return 0;
}

\(T3\):Dilemma (点此看题面

大致题意: 给你一个\(01\)序列,每次能把一个为\(1\)的位置变成\(-1\),将其相邻的\(0\)变成\(1\)、\(1\)变成\(0\)。问是否能把所有位置变成\(-1\)。

结论题?

首先,可以发现,如果把若干个连续\(0\)换成一个\(0\),答案不变,如\(101\)和\(1001\)。

其次,可以发现,若只有长度为偶数的连续\(1\)的序列,是不可以的,如\(1111\),\(01101111110\)。但只要有一个长度为奇数的连续\(1\)的序列,就可以了,如\(111011\)。也就是说,除去长度为偶数的连续\(1\)的序列,答案不变。

也就是说,我们只需考虑长度为奇数的连续\(1\)的序列。

然后画图找找规律,就可以发现当有奇数个长度为奇数的连续\(1\)的序列时可以,否则不可以。

#include<bits/stdc++.h>
#define Tp template<typename Ty>
#define Ts template<typename Ty,typename... Ar>
#define Reg register
#define RI Reg int
#define Con const
#define CI Con int&
#define I inline
#define W while
#define N 100000
#define Gmax(x,y) (x<(y)&&(x=(y)))
using namespace std;
int n;char s[N+5];
int main()
{
RI Tt,i,t=0,res=0;scanf("%d",&Tt);W(Tt--)
{
for(scanf("%s",s),n=strlen(s),t=res=i=0;i^n;++i)
s[i]&1?(t^=1):(res^=t,t=0);puts(res^t?"WIN":"LOSE");//t统计当前连续1序列的奇偶性,res统计长度为奇数的连续1的序列的个数的奇偶性
}return 0;
}

\(T4\):Zombie and the Caves(点此看题面

大致题意: 给你个数组\(C\)以及一个空序列,对于每个\(i\),把序列中第\(i-C_i\sim i+C_i\)个位置都加上\(1\),再给你一个序列,问两个序列中的数是否能一一匹配。

我们先差分求出这个序列,然后排序比较两个序列即可。

这里我用了桶排。

#include<bits/stdc++.h>
#define Tp template<typename Ty>
#define Ts template<typename Ty,typename... Ar>
#define Reg register
#define RI Reg int
#define Con const
#define CI Con int&
#define I inline
#define W while
#define N 100000
#define min(x,y) ((x)<(y)?(x):(y))
#define max(x,y) ((x)>(y)?(x):(y))
using namespace std;
int n,s[N+5],p[N+5];
class FastIO
{
private:
#define FS 100000
#define tc() (A==B&&(B=(A=FI)+fread(FI,1,FS,stdin),A==B)?EOF:*A++)
#define tn (x<<3)+(x<<1)
#define D isdigit(c=tc())
char c,*A,*B,FI[FS];
public:
I FastIO() {A=B=FI;}
Tp I void read(Ty& x) {x=0;W(!D);W(x=tn+(c&15),D);}
Ts I void read(Ty& x,Ar&... y) {read(x),read(y...);}
}F;
int main()
{
RI Tt,i,x,f;F.read(Tt);W(Tt--)
{
for(F.read(n),i=1;i<=n;++i) s[i]=p[i]=0;//清空
for(i=1;i<=n;++i) F.read(x),++s[max(i-x,1)],--s[min(i+x,n)+1];//差分
for(i=1;i<=n;++i) (s[i]+=s[i-1])<=n&&++p[s[i]];//求出序列并存入桶中
for(f=i=1;i<=n;++i) F.read(x),(x>n||!p[x]--)&&(f=0);puts(f?"YES":"NO");//判断是否可以一一匹配
}return 0;
}

\(T5\):Guddu and his Mother(点此看题面

大致题意: 给你一个序列,求有多少组\((i,j,k)\)满足\(xor_{x=i}^{j-1}a_x=xor_{x=j}^ka_x\)。

首先容易发现,对于一组\((i,k)\),若其满足\(xor_{x=i}^ka_x=0\),则对于满足\(i<j\le k\)的任意一组\((i,j,k)\)都是一组合法解,即有\(k-i\)组合法解。

若我们记\(s_i=xor_{x=1}^ia_x\),就相当于\(s_{i-1}\ xor\ s_k=0\),即\(s_{i-1}=s_k\)时,有\(k-i\)组合法解。

也就是当\(s_i=s_k\)时,有\(k-i-1=(k-1)-i\)组合法解。

所以我们开两个\(map\),\(p_x\)表示之前所有满足\(s_i=x\)的\(i\)的和,\(g_x\)表示之前满足\(s_i=x\)的\(i\)的个数。

那么我们枚举\(i\),就可以更新\(ans\)加上\(g_{s_i}(i-1)-p_{s_i}\)。

#include<bits/stdc++.h>
#define Tp template<typename Ty>
#define Ts template<typename Ty,typename... Ar>
#define Reg register
#define RI Reg int
#define Con const
#define CI Con int&
#define I inline
#define W while
#define N 100000
#define LL long long
#define min(x,y) ((x)<(y)?(x):(y))
#define max(x,y) ((x)>(y)?(x):(y))
using namespace std;
int n,s[N+5];map<int,LL> p,g;
class FastIO
{
private:
#define FS 100000
#define tc() (A==B&&(B=(A=FI)+fread(FI,1,FS,stdin),A==B)?EOF:*A++)
#define tn (x<<3)+(x<<1)
#define D isdigit(c=tc())
char c,*A,*B,FI[FS];
public:
I FastIO() {A=B=FI;}
Tp I void read(Ty& x) {x=0;W(!D);W(x=tn+(c&15),D);}
Ts I void read(Ty& x,Ar&... y) {read(x),read(y...);}
}F;
int main()
{
RI Tt,i,x;LL ans;F.read(Tt);W(Tt--)
{
ans=0,p.clear(),g.clear(),p[0]=0,g[0]=1;//清空
for(F.read(n),i=1;i<=n;++i) F.read(x),//读入
s[i]=s[i-1]^x,ans+=1LL*g[s[i]]*(i-1)-p[s[i]],p[s[i]]+=i,++g[s[i]];//统计前缀和,更新答案,更新map
printf("%lld\n",ans);//输出答案
}return 0;
}

\(T6\):Encoding(点此看题面

大致题意: 设\(F(x)\)为\(x\)十进制数位中每段连续相同数字只保留最高位、其余位替换为\(0\)后的值,求\(\sum_{i=l}^rF(i)\)。

显然数位\(DP\)。

我们设\(f_{x,lst}\)和\(g_{x,lst}\)分别表示右数第\(x\)位、上一个数为\(lst\)时的答案和情况数。

考虑记忆化搜索。

对于答案,转移时先将后继状态的\(f\)求和,然后若枚举到这一位的值\(y\)不等于\(lst\),就将答案加上后继状态的\(g\)乘\(y*10^x\)。

对于情况数,直接将后继状态的\(g\)求和即可。

#include<bits/stdc++.h>
#define Tp template<typename Ty>
#define Ts template<typename Ty,typename... Ar>
#define Reg register
#define RI Reg int
#define Con const
#define CI Con int&
#define I inline
#define W while
#define N 100000
#define X 1000000007
#define Inc(x,y) ((x+=(y))>=X&&(x-=X))
using namespace std;
int nl,nr;char L[N+5],R[N+5];
class DigitalDP
{
private:
#define Pr pair<int,int>
#define mp make_pair
#define fir first
#define sec second
int v[N+5],tn[N+5],f[N+5][10],g[N+5][10];
I Pr DP(CI x,CI lst,CI p)//数位DP
{
RI i,lim=p?v[x]:9;Pr t,k=mp(0,0);
if(!x) return mp(0,1);if(!p&&~f[x][lst]) return mp(f[x][lst],g[x][lst]);//若求过答案,直接返回
for(i=0;i<=lim;++i) t=DP(x-1,i,p&&(i==lim)),//枚举这一位填的数,处理后继状态
Inc(k.fir,t.fir),Inc(k.sec,t.sec),i^lst&&(k.fir=(1LL*tn[x]*i%X*t.sec+k.fir)%X);//统计答案和情况数
return f[x][lst]=k.fir,g[x][lst]=k.sec,k;//记忆化,返回答案
}
public:
I DigitalDP() {RI i;for(tn[1]=1,i=2;i<=N;++i) tn[i]=10LL*tn[i-1]%X;}//初始化10的幂
I int GetAns(CI x,char *s)
{
RI i,ans=0;Pr t;for(i=x;i;--i) v[i]=s[x-i]&15;memset(f,-1,sizeof(f));//清空
for(i=0;i<=v[x];++i) t=DP(x-1,i,i==v[x]),ans=(1LL*tn[x]*i%X*t.sec+t.fir+ans)%X;//枚举最高位,这个写法有点蠢啊
return ans;
}
}D;
int main()
{
RI Tt,p;scanf("%d",&Tt);W(Tt--)
{
scanf("%d%s%d%s",&nl,L,&nr,R);p=nl-1;W(L[p]=='0') L[p--]='9';--L[p];//将L-1差分
printf("%d\n",(D.GetAns(nr,R)-D.GetAns(nl,L)+X)%X);//求答案
}return 0;
}

\(T7\):Chef and Gordon Ramsay(点此看题面

大致题意: 求有多少对\((x,y,z)\)满足\(y\)在\(x\)和\(z\)树上最短路径上,且满足给定的相对大小。

考虑一下线段树合并+大分类讨论。

我们先线段树合并,用值域线段树存下每个子树内的所有值。

然后,枚举\(y\),并对\(y\)从大到小的相对排名,以及路径完全在子树内还是部分在子树外,分类讨论:

  • 若\(y\)相对排名为\(1\),求出子树内大于\(y\)的数的个数乘子树外大于\(y\)的数的个数(子树外的可以差分),并枚举子节点加上该儿子的子树内大于\(y\)的数的个数乘其他儿子子树内大于\(y\)的数的个数(其他儿子的可以差分)除以\(2\)。
  • 若\(y\)相对排名为\(2\),求出子树内大于\(y\)的数的个数乘子树外小于\(y\)的数的个数加上求出子树内小于\(y\)的数的个数乘子树外大于\(y\)的数的个数,并枚举子节点加上该儿子的子树内小于\(y\)的数的个数乘其他儿子子树内大于\(y\)的数的个数。
  • 若\(y\)相对排名为\(3\),与相对排名为\(1\)类似,略。

注意卡常,有些用的很多次的值不要每次都到线段树上去查询,可以直接存下来。

#pragma GCC optimize(2)
#include<bits/stdc++.h>
#define Tp template<typename Ty>
#define Ts template<typename Ty,typename... Ar>
#define Reg register
#define RI Reg int
#define Con const
#define CI Con int&
#define I inline
#define W while
#define N 100000
#define LN 20
#define LL long long
#define add(x,y) (e[++ee].nxt=lnk[x],e[lnk[x]=ee].to=y)
using namespace std;
int n,ee,lnk[N+5],Sz[N+5],p[4];LL ans;struct edge {int to,nxt;}e[N<<1];
class FastIO
{
private:
#define FS 100000
#define tc() (A==B&&(B=(A=FI)+fread(FI,1,FS,stdin),A==B)?EOF:*A++)
#define tn (x<<3)+(x<<1)
#define D isdigit(c=tc())
char c,*A,*B,FI[FS];
public:
I FastIO() {A=B=FI;}
Tp I void read(Ty& x) {x=0;W(!D);W(x=tn+(c&15),D);}
Ts I void read(Ty& x,Ar&... y) {read(x),read(y...);}
}F;
template<int SZ,int PS> class SegmentTree//线段树
{
private:
#define LT l,mid,O[rt].S[0]
#define RT mid+1,r,O[rt].S[1]
#define PU(x) (O[x].V=O[O[x].S[0]].V+O[O[x].S[1]].V)
int n,Nt,Rt[SZ+5];struct node {int V,S[2];}O[PS+5];
I void Ins(CI v,CI l,CI r,int& rt)//单点修改
{
if(!rt&&(rt=++Nt,O[rt].S[0]=O[rt].S[1]=0),l==r) return (void)(O[rt].V=1);
RI mid=l+r>>1;v<=mid?Ins(v,LT):Ins(v,RT),PU(rt);
}
I int Qry(CI x,CI y,CI l,CI r,CI rt)//区间求和
{
if(!rt) return 0;if(x<=l&&r<=y) return O[rt].V;RI mid=l+r>>1;
return (x<=mid?Qry(x,y,LT):0)+(y>mid?Qry(x,y,RT):0);
}
I int Merge(CI l,CI r,CI x,CI y)//线段树合并
{
if(!x||!y) return x+y;RI rt=++Nt;if(l==r) return (O[rt].V=O[x].V+O[y].V);RI mid=l+r>>1;
O[rt].S[0]=Merge(l,mid,O[x].S[0],O[y].S[0]),O[rt].S[1]=Merge(mid+1,r,O[x].S[1],O[y].S[1]);
return PU(rt),rt;
}
public:
I void Init(CI _n) {Nt=0,n=_n;for(RI i=1;i<=n;++i) Rt[i]=0;}
I void Ins(CI id,CI v) {Ins(v,1,n,Rt[id]);}
I int Qry(CI id,CI l,CI r) {return Qry(l,r,1,n,Rt[id]);}
I void Merge(CI x,CI y) {Rt[x]=Merge(1,n,Rt[x],Rt[y]);}
};SegmentTree<N,N*LN<<1> S;
I void dfs(CI x,CI lst=0)
{
RI i;for(Sz[x]=1,S.Ins(x,x),i=lnk[x];i;i=e[i].nxt)//处理子树,合并子树线段树
e[i].to^lst&&(dfs(e[i].to,x),Sz[x]+=Sz[e[i].to],S.Merge(x,e[i].to),0);
LL res=0;RI t,t1=S.Qry(x,1,x-1),t2=Sz[x]-t1-1;
if(p[2]==1)//若y相对排名为1
{
ans+=1LL*(n-x-t2)*t2;//部分在子树外
for(RI i=lnk[x];i;i=e[i].nxt) e[i].to^lst&&//完全在子树内
(t=S.Qry(e[i].to,x+1,n),res+=1LL*(t2-t)*t);
}
else if(p[2]==2)//若y相对排名为2
{
ans+=1LL*(n-x-t2)*t1+1LL*(x-1-t1)*t2;//部分在子树外
for(RI i=lnk[x];i;i=e[i].nxt) e[i].to^lst&&//完全在子树内
(t=S.Qry(e[i].to,x+1,n),res+=1LL*(t2-t)*(Sz[e[i].to]-t));
}
else//若y相对排名为3
{
ans+=1LL*(x-1-t1)*t1;//部分在子树外
for(RI i=lnk[x];i;i=e[i].nxt) e[i].to^lst&&//完全在子树内
(t=S.Qry(e[i].to,1,x-1),res+=1LL*(t1-t)*t);
}ans+=res>>(p[2]!=2);
}
int main()
{
RI Tt,i,x,y;F.read(Tt);W(Tt--)
{
for(F.read(n),S.Init(n),ee=0,i=1;i<=n;++i) lnk[i]=0;//清空
for(i=1;i<=3;++i) F.read(p[i]);for(i=1;i^n;++i) F.read(x,y),add(x,y),add(y,x);//读入建边
ans=0,dfs(1),printf("%lld\n",ans);//输出答案
}return 0;
}

【CodeChef】August Challenge 2019 Div2 解题报告的更多相关文章

  1. 【CodeChef】December Challenge 2019 Div1 解题报告

    点此进入比赛 这次比赛本来想好好打的,但不幸的是,这周先是要认真复习准备月考,考完又是发烧在床上躺了一个周末,所以最终没能打完. 我还是好弱啊. \(T1\):Binary XOR(点此看题面) 大致 ...

  2. Codechef August Challenge 2019 Division 2

    Preface 老年菜鸡终于开始打CC了,由于他太弱了所以只能打Div2 因为台风的原因challenge并没有写,所以水了个Rank7 A Football SB模拟题不解释 #include< ...

  3. Codechef August Challenge 2019 Chef and Gordon Ramsay

    [传送门] 题目即求所有的三元组,相对大小关系同 $p_1,p_2,p_3$. 题解说都很清楚,这里写一下过程整理一下思路. 如果我们枚举中间这个元素,那么就是统计子树内外有多少个大于这个数和小于这个 ...

  4. Codechef April Challenge 2019 游记

    Codechef April Challenge 2019 游记 Subtree Removal 题目大意: 一棵\(n(n\le10^5)\)个结点的有根树,每个结点有一个权值\(w_i(|w_i\ ...

  5. Codechef September Challenge 2019 Division 2

    Preface 这确实应该是我打过的比较水的CC了(其实就打过两场) 但由于我太弱了打的都是Div2,所以会认为上一场更简单,其实上一场Div的数据结构是真的毒 好了废话不多说快速地讲一下 A Eas ...

  6. codeforce 192 div2解题报告

    今天大家一起做的div2,怎么说呢,前三题有点坑,好多特判.... A. Cakeminator 题目的意思是说,让你吃掉cake,并且是一行或者一列下去,但是必须没有草莓的存在.这道题目,就是判断一 ...

  7. CodeChef April Challenge 2019题解

    传送门 \(Maximum\ Remaining\) 对于两个数\(a,b\),如果\(a=b\)没贡献,所以不妨假设\(a<b\),有\(a\%b=a\),而\(b\%a<a\).综上, ...

  8. Codeforces #263 div2 解题报告

    比赛链接:http://codeforces.com/contest/462 这次比赛的时候,刚刚注冊的时候非常想好好的做一下,可是网上喝了个小酒之后.也就迷迷糊糊地看了题目,做了几题.一觉醒来发现r ...

  9. Crypto Challenge Set 1解题报告

    1.Convert hex to base64 题意:给出一个hex编码过的字符串,将它进行base64加密 解题关键:直接利用base64库函数实现 import base64 str1=" ...

随机推荐

  1. ENDGAME

    "So if I were to wrap this up tight with a bow or whatever,I guess I'd say my career of OI was ...

  2. Django3.0 前瞻 支持异步通信

    最近两年,Django的版本号提升得特别快,2.0还没有多久,很快就要到3.0了. 让我们先看看官方的路线图和时间表: 版本号 发布日期 停止更新日期 停止维护日期 3.0 2019-12 2020- ...

  3. IT兄弟连 Java语法教程 数组 什么是数组

    数组是编程语言中最常见的一种数据结构,可用于存储多个数据,每个数组元素存放一个数据,通常可通过数组元素的索引来访问数组元素,包括为数组元素赋值和取出数组元素的值.Java语言的数组则具有其特有的特征, ...

  4. pytest框架优化——清理历史截图图片和allure报告文件

    痛点分析: 当我们每次执行完用例的时候,如果出现bug或者是测试脚本出了问题,一般会通过测试报告.异常截图.日志来定位分析,但是我们发现运行次数多了之后,异常截图和测试报告会不停地增多,对我们定位分析 ...

  5. ASP.NET(1)

    1.IIS安装问题,先装VS再装IIS,处理程序映射有问题,使用VS自带的控制台输入命令,注册路径 2.开发模式,一般处理程序,使用IO操作读取html文件,使前后端分离 3.post请求和get请求 ...

  6. 软件设计之基于Java的连连看小游戏(二)——游戏基础界面的制作及事件的添加

    上次完成到游戏首页的制作,今天完成了游戏基础界面的制作以及事件的简单添加.由于功能尚未完全实现,因此游戏界面的菜单列表只是简单地添加了一下,其余菜单列表以及倒计时等在后续的制作中逐一完善. 1.首先在 ...

  7. Define the Data Model and Set the Initial Data 定义数据模型并设置初始数据

    This topic describes how to define the business model and the business logic for WinForms and ASP.NE ...

  8. JavaWeb之Servlet(3)

    Servlet(3) HttpServletRequest 该类的对象封装了所以客户端提交过来的数据 获取所有请求头数据 public java.util.Enumeration<E> g ...

  9. Javase之集合体系之(1)集合顶层类Collection与其迭代器知识

    集合体系之集合顶层类Collection与其迭代器知识 集合的由来:Java是一门面向对象语言,而面向对象语言对事物的描述是通过对象体现的,为了方便对多个对象进行操作,就必须把多个对象进行存储,而要存 ...

  10. HTTP协议中的chunked编码解析

    \r\n\r\n"了. chunked编码很简单,是不是? 不过,在协议还原的实现过程中,如何高效高性能地对chunked进行解码,是一件值得挑战的事哦.毕竟,HTTP的流量占比不小的. 长 ...