【题解】bzoj-3884 上帝与集合的正确做法

模指数塔问题解析
本文探讨了一种特殊的模指数塔问题,即求解形如2^(2^(2^(...))) mod p的问题。通过引入欧拉函数及其性质,文章提供了一种有效的递归求解策略,并给出了具体的实现代码。

Problem

to bzoj

求值:

2222...modp 2 2 2 2 . . . mod p

Solution

看到无限的 2 2 就很2啊,最初想法是感觉是找循环节,觉得应该会稳定在一个数

看了skywalkert dalao的博客蒟蒻才渐渐顿悟

2222...(modp)=2222...2ϕ(p)t(modp)=2222...(modϕ(p))(modp) 2 2 2 2 . . . ( mod p ) = 2 2 2 2 . . . 2 ϕ ( p ) ∗ t ( mod p ) = 2 2 2 2 . . . ( mod ϕ ( p ) ) ( mod p )

这样在指数的位置 222...modϕ(p) 2 2 2 . . . mod ϕ ( p ) 又和原式一样了

只有 pϕp p → ϕ p ,当 p=0 p = 0 时,答案为 0 0

这样递归求解即可

这样要求2 p p 互质,如果p为偶数,算法就不成立

那就把 p p 中的2因子拆分:令 p=2k·d p = 2 k · d

2222...(mod2k·d)=2k·2222...k(modϕ(d)) 2 2 2 2 . . . ( mod 2 k · d ) = 2 k · 2 2 2 2 . . . − k ( mod ϕ ( d ) )

2k 2 k 放在外面,再递归求解

2222...k(modϕ(d))=(2222...modϕ(d)kmodϕ(d))modϕ(d) 2 2 2 2 . . . − k ( mod ϕ ( d ) ) = ( 2 2 2 2 . . . mod ϕ ( d ) − k mod ϕ ( d ) ) mod ϕ ( d )

其中 2222...modϕ(d) 2 2 2 2 . . . mod ϕ ( d ) 可以递归求解,直到 p=1ans=0 p = 1 ⇔ a n s = 0

#include<bits/stdc++.h>
using namespace std;
typedef long long ll;
#define rg register

template <typename _Tp> inline void read(_Tp&x){
    rg char c11=getchar(),ob=0;x=0;
    while(c11^'-'&&!isdigit(c11))c11=getchar();if(c11=='-')c11=getchar(),ob=1;
    while(isdigit(c11))x=x*10+c11-'0',c11=getchar();if(ob)x=-x;return ;
}

inline int phi(int x){
    int res=x;
    for(rg int i=2;i*i<=x;++i)
        if(x%i==0){
            res=res/i*(i-1);
            while(x%i==0)x/=i;
        }
    if(x^1)res=res/x*(x-1);
    return res;
}

int qpow(int A,int B,int p){
    int ans=1;
    while(B){
        if(B&1)ans=(ll)ans*A%p;
        A=(ll)A*A%p;
        B>>=1;
    }
    return ans;
}

int work(int p){
    if(p==1)return 0;
    rg int tmp=0,ans=0;
    while(!(p&1))++tmp,p>>=1;
    rg int phip=phi(p);
    ans=(ll)(work(phip)+phip-tmp%phip)%phip;
    ans=qpow(2,ans,p);
    return ans<<tmp;
}

int main(){
    rg int T;rg int p;
    read(T);
    while(T--)read(p),printf("%d\n",work(p)%p);
    return 0;
}
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值