@TOC
笔记
例题
题目
Problem Description
There are n lights in a circle numbered from 1 to n. The left of light 1 is light n, and the left of light k (1< k<= n) is the light k-1.At time of 0, some of them turn on, and others turn off.
Change the state of light i (if it’s on, turn off it; if it is not on, turn on it) at t+1 second (t >= 0), if the left of light i is on !!! Given the initiation state, please find all lights’ state after M second. (2<= n <= 100, 1<= M<= 10^8)
Input
The input contains one or more data sets. The first line of each data set is an integer m indicate the time, the second line will be a string T, only contains ‘0’ and ‘1’ , and its length n will not exceed 100. It means all lights in the circle from 1 to n.
If the ith character of T is ‘1’, it means the light i is on, otherwise the light is off.
Output
For each data set, output all lights’ state at m seconds in one line. It only contains character ‘0’ and '1.
Sample Input
1
0101111
10
100000001
Sample Output
1111000
001000010
易错点
首先要想出状态转移方程,才能想到用快速幂矩阵。
要注意的点:
1,快速幂里ans要初始化为单位矩阵(对角线为1);
2,输入数据为多组时注意初始化!!!
代码
#include <iostream>
#include <string>
#include <cstring>
using namespace std;
int anss[105];
int sta[105];
struct mapp
{
int arr[105][105];
int n;
mapp()
{
n = 0;
memset(arr,0,sizeof(arr));
}
};
mapp mul(mapp a,mapp b)
{
mapp an;
an.n = a.n;
for(int i = 0;i < a.n;i++)
for(int j = 0;j < a.n;j++)
for(int k = 0;k < a.n;k++)
{
an.arr[i][j]=(an.arr[i][j]+(a.arr[i][k]*b.arr[k][j])%2)%2;
}
return an;
}
mapp fastpow(mapp a,int m)
{
mapp ans;
ans.n=a.n;
for(int i = 0;i < ans.n;i++)
{
ans.arr[i][i] = 1;
}
while(m > 0)
{
if(m&1)
{
ans=mul(a,ans);
}
m >>= 1;
a = mul(a,a);
}
return ans;
}
int main()
{
std::ios::sync_with_stdio(false);
int m;
string s;
while(cin >> m)
{
memset(anss,0,sizeof anss);
cin >> s;
int len = s.length();
for(int i = 0;i < len;i++)
{
sta[i] = s[i]-'0';
}
mapp x=mapp();
x.n = len;
x.arr[0][0]=1;
x.arr[0][len-1]=1;
for(int i = 1;i < len;i++)
x.arr[i][i] = x.arr[i][i-1] = 1;
mapp xx = fastpow(x,m);
for(int i = 0;i < len;i++)
{
for(int j = 0;j < len;j++)
anss[i] = (anss[i]+xx.arr[i][j]*sta[j])%2;
}
for(int i = 0;i < len;i++)
cout << anss[i];
cout << endl;
}
return 0;
}