POJ-1721 CARDS 置换群分数幂运算
题目链接:http://poj.org/problem?id=1721
置换群的分数幂运算,分数幂运算考虑的是置换的合并,但这道题简化了很多,首先注意到“Alice first writes down all the numbers from 1 to N in some random order: a1, a2, ..., aN. Then she arranges the cards so that the position ai holds the card numbered ai+1, for every 1 <= i <= N-1, while the position aN holds the card numbered a1.”,即置换只有一个循环节且长度 l 为奇数,其次开放数为2。则有gcd(l,2)=1,即永远都只有一个循环节,直接模拟就可以了。
1 //STATUS:C++_AC_63MS_192KB 2 #include<stdio.h> 3 #include<stdlib.h> 4 #include<string.h> 5 #include<math.h> 6 #include<iostream> 7 #include<string> 8 #include<algorithm> 9 #include<vector> 10 #include<queue> 11 #include<stack> 12 #include<map> 13 using namespace std; 14 #define LL __int64 15 #define pii pair<int,int> 16 #define Max(a,b) ((a)>(b)?(a):(b)) 17 #define Min(a,b) ((a)<(b)?(a):(b)) 18 #define mem(a,b) memset(a,b,sizeof(a)) 19 #define lson l,mid,rt<<1 20 #define rson mid+1,r,rt<<1|1 21 const int N=1010,INF=0x3f3f3f3f,MOD=10000,STA=8000010; 22 const LL LNF=0x3f3f3f3f3f3f3f3f; 23 const double DNF=1e13; 24 25 int T[2][N],vis[N],C[N]; 26 int n,s; 27 28 int main() 29 { 30 // freopen("in.txt","r",stdin); 31 int i,j,k,p,u,d; 32 while(~scanf("%d%d",&n,&s)) 33 { 34 for(i=1;i<=n;i++) 35 scanf("%d",&T[0][i]); 36 37 p=1; 38 while(s--){ 39 mem(vis,0); 40 for(i=1;i<=n;i++){ 41 if(!vis[i]){ 42 mem(vis,0); 43 u=i;k=0; 44 while(!vis[u]){ 45 vis[u]=1; 46 C[k++]=u; 47 u=T[!p][u]; 48 } 49 d=(k+1)/2; 50 for(j=0;j<k;j++){ 51 T[p][C[j]]=C[(j+d)%k]; 52 } 53 } 54 } 55 p=!p; 56 } 57 58 p=!p; 59 for(i=1;i<=n;i++) 60 printf("%d\n",T[p][i]); 61 } 62 return 0; 63 }