題解 P2227 【[HNOI2001]洗牌機】
阿新 • • 發佈:2020-07-21
Solution [HNOI2001]洗牌機
題目大意:給定一個長為\(n\)的只有一個輪換的置換,告訴你平方\(s\)次之後的結果,求原置換
置換開方
詳見《潘震皓:置換群快速冪運算研究與探討》(2005年國集論文)
關鍵在於如果一個長為\(n\)的置換\(T\)只有一個輪換,那麼\(T^n=I\),I為單位置換
所以\(\sqrt{T}=\sqrt{T^{n+1}}=T^{\frac{n+1}{2}}\)
快速冪即可,複雜度\(O(snlogn)\)
#include <cstdio> using namespace std; const int maxn = 1024; int n,s; struct Node{ int val[maxn]; Node operator * (const Node &rhs)const{ Node res; for(int i = 1;i <= n;i++) res.val[i] = rhs.val[val[i]]; return res; } }now; inline Node qpow(Node a,int b){ Node res,base = a; for(int i = 1;i <= n;i++)res.val[i] = i; while(b){ if(b & 1)res = res * base; base = base * base; b >>= 1; } return res; } int main(){ scanf("%d %d",&n,&s); for(int i = 1;i <= n;i++)scanf("%d",now.val + i); for(int i = 1;i <= s;i++)now = qpow(now,(n + 1) >> 1); for(int i = 1;i <= n;i++) printf("%d%c",now.val[i]," \n"[i == n]); return 0; }