• [AHOI2005]洗牌


    链接:https://www.luogu.com.cn/problem/P2054

    设 n=2m

    为了方便进行有关剩余系的推导

    把原本的标号
    1.....2m

    改为
    0......2m-1

    分类讨论一下

    原本在位置x的牌

    经过一次洗牌后

    会出现在什么位置

    这个式子还是比较好推的

    分类讨论可得

    [egin{align*} x<m &: y= 2x + 1 \ xge m &: y= 2x - 2m end{align*} ]

    然后用一些数学技巧处理一下

    [egin{align*} x<m &: y= 2x + 1 \ xge m &: y= 2x + 1 -(2m+1) end{align*} ]

    然后发现这个式子就等价于

    [yequiv{ 2x + 1 } pmod {2m+1} ]

    用一些简单的数列技巧处理

    [y+1equiv{ 2(x + 1) } pmod {2m+1} ]

    所以

    [X_nequiv{X_0 * 2^M} pmod {2m+1} ]

    然后问题就转化为一个解同余方程了

    恶心的地方在于这个题目的数据范围比较恶心

    会爆long long
    所以得用一下龟速乘法

    #include<bits/stdc++.h>
    #define N 110000
    #define eps 1e-7
    #define inf 1e9+7
    #define db double
    #define ll long long
    #define ldb long double
    #define ull unsigned long long
    using namespace std;
    inline ll read()
    {
    	char ch=0;
    	ll x=0,flag=1;
    	while(!isdigit(ch)){ch=getchar();if(ch=='-')flag=-1;}
    	while(isdigit(ch)){x=(x<<3)+(x<<1)+ch-'0',ch=getchar();}
    	return x*flag;
    }
    ll mo;
    ll ksc(ll x,ll y,ll p){return ((x*y-(ll)(((ldb)x*y+0.5)/p)*p)%p+p)%p;}
    ll ksm(ll x,ll k)
    {
    	ll ans=1;
    	while(k)
    	{
    		if(k&1)ans=ksc(ans,x,mo);
    		k>>=1;x=ksc(x,x,mo);
    	}
    	return ans;
    }
    ll X,Y;
    ll exgcd(ll a,ll b)
    {
    	if(!b){X=1;Y=0;return a;}
    	ll d=exgcd(b,a%b),t=X;
    	X=Y;Y=t-(a/b)*Y;
    	return d; 
    }
    int main()
    {
    	ll n=read(),m=read(),l=read();mo=n+1;
    	ll a=ksm(2,m),b=mo,d=exgcd(a,b),p1=b/d;
    	X=(X%p1+p1)%p1;X=ksc(X,(l/d),p1);
    	printf("%lld",X);
    	return 0;
    }
    
  • 相关阅读:
    ubuntu 16.04 tmux
    ubuntu 16.04 samba 文件共享
    ubuntu 16.04 有道词典
    ubuntu bless 16字节每行
    Win7任务栏图标大小调整为等宽
    ubuntu 16.04 vnc server
    ubuntu 16.04 U盘多媒体不自动弹出
    Linux录屏软件
    通过apt-get安装nvidia驱动
    调试X Server
  • 原文地址:https://www.cnblogs.com/Creed-qwq/p/13469135.html
Copyright © 2020-2023  润新知