模拟赛题解锦集——Hzoi
Posted
tags:
篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了模拟赛题解锦集——Hzoi相关的知识,希望对你有一定的参考价值。
Day IXV:
T1:
对于二者之一$n$,每次选取要么变成$2n$,要么是$n-(tot-n)=2*n-tot$,即最后结果为$n*2^{k}(\mod tot)$.
T2:
思博题。枚举每个右边界$pos$,求其左边界$l[pos]$,显然其左边界应该是$l[pos-1]$和最后一个满足$a_{x}-K$为$a_{pos}$的倍数之间取一个较大值,然后用该数更新一下边界位置即可。
T3:
其实DP是蛮裸的,可惜第一题浪费时间太久,最后半个小时想法已经很接近答案,但是也没怎么细想,这是今天最大的失误。
设$f_{i,j}$表示前$i$层已经选好且第$i$层恰好选取了$j$种颜色的全部方案,再设两个辅助数组$g_{i,j},gc_{i,j}$。其中$g_{i,j}$表示长度为i的装饰品,只使用确定的j种颜色的方案数,$gc$则表示任意j种颜色的方案数。
然后我们很容易得到一个递推式:$f_{i,j}=gc_{i,j}\sum_{x=1}^{a[i-1]}f_{i-1,x}-g_{i,j}f_{i-1,j}$。
再考虑如何得到$g$和$gc$数组。考虑组合意义:$g_{i,j}=g_{i-1,j}(j-1)+g_{i-1,j-1}j$,$gc_{i,j}=g_{i,j}*(_{j}^{m})$。但是此题模数不保证为质数,所以组合数不好处理,换一种思路$gc_{i,j}=gc_{i-1,j}(j-1)+gc_{i-1,j-1}(m-j+1)$。
然后就可以$O(max(a_{i})^2+S)$解决问题了。
代码:
T1:
1 #include <cstdio> 2 int n,m,k,x=2; 3 int main(){ 4 scanf("%d%d%d",&n,&m,&k),m=n+m; 5 for(;k;(k&1)?n=1ll*n*x%m:0,k>>=1,x=1ll*x*x%m); 6 printf("%d",n<m-n?n:m-n); 7 }
T2:
1 #define Troy 10/14/2017 2 3 #include <bits/stdc++.h> 4 5 using namespace std; 6 7 inline int read(){ 8 int s=0,k=1;char ch=getchar(); 9 while(ch<‘0‘||ch>‘9‘) k=ch==‘-‘?-k:k,ch=getchar(); 10 while(ch>47&&ch<=‘9‘) s=s*10+(ch^48),ch=getchar(); 11 return s*k; 12 } 13 14 typedef long long ll; 15 16 const int N=1e5+7; 17 18 int n,k,a[N],l[N],r[N]; 19 int last[N]; 20 21 inline void add(int x,int pos){ 22 if(x<0) return ; 23 if(x==0){ 24 last[x]=pos; 25 return ; 26 } 27 for(int i=1;1ll*i*i<=x;i++){ 28 if(x%i==0) 29 last[i]=pos,last[x/i]=pos; 30 } 31 } 32 33 int main(){ 34 n=read(),k=read(); 35 for(int i=1;i<=n;i++) 36 a[i]=read(); 37 l[0]=1; 38 for(int i=1;i<=n;i++){ 39 if(a[i]>k) 40 l[i]=max(max(last[a[i]],last[0])+1,l[i-1]); 41 else 42 l[i]=l[i-1]; 43 add(a[i]-k,i); 44 } 45 ll ans=0; 46 for(int i=1;i<=n;i++) 47 ans=ans+(i-l[i]+1); 48 printf("%lld\n",ans); 49 }
T3:
1 #define Troy 10/14/2017 2 3 #include <cstdio> 4 #include <vector> 5 6 using namespace std; 7 8 inline int read(){ 9 int s=0,k=1;char ch=getchar(); 10 while(ch<‘0‘||ch>‘9‘) k=ch==‘-‘?-k:k,ch=getchar(); 11 while(ch>47&&ch<=‘9‘) s=s*10+(ch^48),ch=getchar(); 12 return s*k; 13 } 14 15 typedef long long ll; 16 17 const int N=5e3+7; 18 19 int n,m,p,a[(int)1e6+7],f[2][N],gc[N][N],g[N][N]; 20 21 int main(){ 22 n=read(),m=read(),p=read(); 23 for(int i=1;i<=n;i++) 24 a[i]=read(); 25 g[0][0]=1; 26 gc[0][0]=1; 27 for(int i=1;i<=5000;i++){ 28 for(int j=1;j<=min(i,m);j++){ 29 g[i][j]=(1ll*g[i-1][j]*(j-1)+1ll*g[i-1][j-1]*j)%p, 30 gc[i][j]=(1ll*gc[i-1][j]*(j-1)%p+1ll*gc[i-1][j-1]*(m-j+1)%p)%p; 31 } 32 } 33 f[0][0]=1; 34 int now=1,last=0; 35 for(int i=1;i<=n;i++){ 36 for(int j=1;j<=a[i];j++){ 37 f[now][j]=1ll*f[last][0]*gc[a[i]][j]%p; 38 if(a[i-1]>=j) 39 f[now][j]-=1ll*f[last][j]*g[a[i]][j]%p; 40 f[now][j]=(f[now][j]%p+p)%p; 41 42 f[now][0]=(f[now][0]+f[now][j])%p; 43 f[last][j]=0; 44 } 45 f[last][0]=0,now^=1,last^=1; 46 } 47 printf("%d\n",f[last][0]); 48 } 49 /* 50 3 2 1000 51 3 1 2 52 */
以上是关于模拟赛题解锦集——Hzoi的主要内容,如果未能解决你的问题,请参考以下文章
HZOI20190908模拟40 队长快跑,影魔,抛硬币 题解