题意就是有长度为L的序列,每位的取值可以是'f'或者'm',问不包含'fff'和'fmf'的个数。

打表找规律

FJUT2019暑假周赛一题解

不难找出递推公式为F[n] = F[n-1] + F[n-3] + F[n-4]。

然后直接遍历就可以了...突然发现L范围很小,我写了个矩阵快速幂...

多组数据且模数不固定,矩阵快速幂即可

 

  1 #include <bits/stdc++.h>
  2 using namespace std;
  3 typedef long long ll;
  4 
  5 int n,mod;
  6 
  7 struct M {
  8     ll p[4][4];
  9     M(int num) {
 10         memset(p,0,sizeof p);
 11         for (int i = 0; i < 4; i++) {
 12             p[i][i] = num;
 13         }
 14     }
 15 
 16     M operator * (M b) {
 17         M c(0);
 18         for (int i = 0; i < 4; i++) {
 19             for (int j = 0; j < 4; j++) {
 20                 c.p[i][j] = 0;
 21                 for (int k = 0; k < 4; k++) {
 22                     c.p[i][j] = (c.p[i][j] + (p[i][k]*b.p[k][j])%mod)%mod;
 23 
 24                 }
 25             }
 26         }
 27         return c;
 28     }
 29 
 30     M operator ^ (ll k) {
 31         M c(1),a = *this;
 32         while (k) {
 33             if (k&1) {
 34                 c = a*c;
 35             }
 36             a = a*a;
 37             k >>= 1;
 38         }
 39         return c;
 40     }
 41 
 42 };
 43 M a(0),b(0);
 44 int solve() {
 45     M c(0);
 46 
 47     if (n == 0) {
 48         return 0;
 49     } else if (n <= 4) {
 50         return a.p[4-n][0]%mod;
 51     }
 52     c = b^(n-4);
 53     c = c*a;
 54     return c.p[0][0]%mod;
 55 }
 56 
 57 string s;
 58 
 59 void db() {
 60     for (int i = 1; i <= 15; i++) {
 61         int p = pow(2.0,i),tot = 0,cnt = 0;
 62         for (int j = 0; j < p; j++) {
 63             int tmp = 1;
 64             s = "";
 65             for (int k = 1; k <= i; k++) {
 66                 if (tmp&j) {
 67                     s += 'f';
 68                 } else {
 69                     s += 'm';
 70                 }
 71                 tmp <<= 1;
 72             }
 73             for (int k = 0; k < int(s.size())-2; k++) {
 74                 if (s[k] =='f' && s[k+1] == 'm' && s[k+2] == 'f') {
 75                     cnt++;
 76                     break;
 77                 } else if (s[k] =='f' && s[k+1] == 'f' && s[k+2] == 'f') {
 78                     cnt++;
 79                     break;
 80                 }
 81             }
 82             tot++;
 83         }
 84         cout << i << ' ' << p-cnt << endl;
 85     }
 86 }
 87 /*
 88     f_i = f_{i-1} + f_{i-3} +f_{i-4};
 89     1 0 1 1
 90     1 0 0 0
 91     0 1 0 0
 92     0 0 1 0
 93 */
 94 int main() {
 95     ios_base::sync_with_stdio(0);
 96     cin.tie(0);
 97     db();
 98 
 99     a.p[0][0] = 9;
100     a.p[1][0] = 6;
101     a.p[2][0] = 4;
102     a.p[3][0] = 2;
103     b.p[0][0] = 1;
104     b.p[0][2] = 1;
105     b.p[0][3] = 1;
106     b.p[1][0] = 1;
107     b.p[2][1] = 1;
108     b.p[3][2] = 1;
109     while (cin >> n >> mod) {
110         cout << solve() << endl;
111     }
112     return 0;
113 }
View Code

相关文章: