【bzoj1965】【AHOI2005】洗牌
来源:互联网 发布:怎样做seo 编辑:程序博客网 时间:2024/05/20 07:33
题意
有一副牌,共
n 张(n 为偶数),每一次洗牌将其均分为上下两叠,然后取下叠第一张为新的第一张,上叠第一张为新的第二张,下叠第二张为新的第三张……求经过m 次洗牌后,第l 张牌的面值(初始为【1,n】 )
解法
模拟:
这道题比较容易,只要能够一步一步地分析下去:
首先可以知道,对于现在处于第x 张的牌来说,有:
①.若其在上叠(x≤n2 ),那么洗牌后它将会去到2∗x 的位置
②.若其在下叠(x>n2 ),那么洗牌后它将会去到2∗x−1 的位置
所以,最暴力的做法:开一个滚动数组,不停地向前模拟,得分20%
如果将上面的式子变形,可以得到,对于现在处于第x 张的牌来说,有:
①.若x 为奇数,那么在洗牌前,这一张牌的位置是:n+x+12
②.若x 为偶数,那么在洗牌前,这一张牌的位置是:x2
所以高级一点的暴力就是采用递归,不停的求解,由于爆栈,所以得分50%
如果将递归改为递推,那么可以得到70% ,最后的三个点会超时
继续考虑优化:一个数x 经过若干次变化之后,必定又会变回x ,我们假设经过n+1 次洗牌,那么x 已经变化n+1 次,而至多只有n 个数,所以肯定又会变回去
于是我们首先模拟找到变化的循环节,然后用m 对循环节取余,然后剩下的余数部分再次暴力模拟即可
复杂度
O(
klogm ),k 为一不确定数字,大概在【1,1000】
20分代码
#include<iostream>#include<cstdlib>#include<cstdio>using namespace std;const int MAXN=10000010;int w[2][MAXN];int n,m,l,cur;int main(){ scanf("%d%d%d",&n,&m,&l); for(int i=1;i<=n;i++) w[0][i]=i; while( m-- ) { for(int i=1;i<=n/2;i++) w[cur^1][2*i]=w[cur][i]; for(int i=1;i<=n/2;i++) w[cur^1][2*i-1]=w[cur][i+n/2]; cur^=1; } printf("%d\n",w[cur][l]); return 0;}
50分代码
#include<iostream>#include<cstdlib>#include<cstdio>using namespace std;const int MAXN=10000010;int n,m,l,ans;void work(int k,int pos){ if( !k ) { ans=pos;return ; } if( pos%2 ) work( k-1,n/2+(pos+1)/2 ); else work( k-1,pos/2 );}int main(){ scanf("%d%d%d",&n,&m,&l); work( m,l ); printf("%d\n",ans); return 0;}
70分代码
#include<iostream>#include<cstdlib>#include<cstdio>using namespace std;int n,m,l;int main(){ scanf("%d%d%d",&n,&m,&l); for(int i=1;i<=m;i++) { if( l%2 ) l=n/2+(l+1)/2; else l=l/2; } printf("%d\n",l); return 0;}
100分代码
#include<iostream>#include<cstdlib>#include<cstdio>#define Lint long long intusing namespace std;Lint n,m,l,x,cnt=1;int main(){ scanf("%d%d%d",&n,&m,&l); if( l%2 ) x=n/2+(l+1)/2; else x=l/2; while( x!=l ) { cnt++; if( x%2 ) x=n/2+(x+1)/2; else x=x/2; } m=m%cnt; for(int i=1;i<=m;i++) if( l%2 ) l=n/2+(l+1)/2; else l=l/2; printf("%d\n",l); return 0;}
- bzoj1965: [Ahoi2005]SHUFFLE 洗牌
- [BZOJ1965][Ahoi2005]SHUFFLE 洗牌
- BZOJ1965: [Ahoi2005]SHUFFLE 洗牌
- bzoj1965 [Ahoi2005]SHUFFLE 洗牌
- bzoj1965: [Ahoi2005]SHUFFLE 洗牌
- 【bzoj1965】【AHOI2005】洗牌
- BZOJ1965 [Ahoi2005]SHUFFLE 洗牌
- 【bzoj1965】【Ahoi2005】【SHUFFLE 洗牌】【快速幂】
- [BZOJ1965][Ahoi2005]SHUFFLE 洗牌(数学相关)
- [BZOJ1965][Ahoi2005]SHUFFLE 洗牌 数学公式+乘法逆元
- BZOJ1965 洗牌
- 1965: [Ahoi2005]SHUFFLE 洗牌
- 1965: [Ahoi2005]SHUFFLE 洗牌
- Ahoi2005 洗牌 扩展欧几里得
- 【BZOJ1965】【codevs1446】洗牌,快速幂+扩展欧几里德
- bzoj 1965: [Ahoi2005]SHUFFLE 洗牌
- 【BZOJ】【P1965】【AHOI2005】【SHUFFLE 洗牌】【题解】【数论】
- BZOJ 1965 AHOI2005 SHUFFLE 洗牌 数论
- springmvc的ModelAttribute注解
- 安卓笔记(1)文字超链接
- 校招准备系列:每天一道算法题(10)-二维数组查找
- C语言程序的基本结构--HelloWrold篇
- C++ STL之deque解析(1)---《C++ STL》
- 【bzoj1965】【AHOI2005】洗牌
- (M)Dynamic Programming,DFS:Shopping Offers
- Java并发实战:Callable+FutureTask实现多线程判分汇总
- 关于GAN网络的隐空间维度选择问题
- 《Redis的主从复制》原理详解
- c++知识点---文件的简单读写
- SpringMVC拦截器(资源和权限管理)
- 7.查询性能优化
- linux运维面试必备