vijosP1049 送给圣诞夜的礼品
【思路】
快速幂+矩阵转换。
将m次矩阵的转换看作是一次快速幂中的乘法操作,这样可以用O(log(k/m))的时间求出矩阵进行k/m次操作后的结果,然后把剩下的k%m次矩阵转换补上即可。
【代码】
1 #include<iostream> 2 #include<cstring> 3 #define FOR(a,b,c) for(int a=(b);a<=(c);a++) 4 using namespace std; 5 6 const int maxn = 100+10; 7 8 int op[11][maxn]; 9 int _hash[maxn],tmp[maxn],tmp2[maxn],ans[maxn]; 10 int n,m,k; 11 12 void calc(int*A,int*B) { //据B操作改变A 13 FOR(i,1,n) tmp2[i]=A[B[i]]; 14 FOR(i,1,n) A[i]=tmp2[i]; 15 } 16 17 int main() { 18 ios::sync_with_stdio(false); 19 cin>>n>>m>>k; 20 FOR(i,1,m) FOR(j,1,n) cin>>op[i][j]; 21 22 FOR(i,1,n) _hash[i]=ans[i]=i; //init 23 24 FOR(i,1,m) calc(_hash,op[i]); //calc_hash 25 26 int T=k/m; k %= m; 27 28 memcpy(&tmp,&_hash,sizeof(_hash)); //tmp=1 29 while(T) { 30 if(T&1) calc(ans,tmp); //ans*=tmp 31 calc(tmp,tmp); //tmp*=tmp 32 T>>=1; 33 } 34 FOR(i,1,k) calc(ans,op[i]); 35 36 FOR(i,1,n) cout<<ans[i]<<" "; 37 return 0; 38 }