题目要求:y = (5 + 2√6)1+2^x
设An=(5 + 2√6)n,Bn=(5 - 2√6)n
Cn = An + Bn
显然Cn是正整数,且Bn是小于1的
所以我们所求的答案其实就是Cn - 1
通过推导:
Cn * [(5 + 2√6) + (5 - 2√6)] =
((5 + 2√6)n + (5 - 2√6)n) * [(5 + 2√6) + (5 - 2√6)] =
(5 + 2√6)n + 1 + (5 - 2√6)n + 1) + (5 + 2√6)n - 1 + (5 - 2√6)n - 1)
10 * Cn = Cn + 1 + Cn - 1
Cn + 1 = 10 * Cn - Cn-1
我们找出了递推式,然后我们发现指数特别的大,M是个素数
于是我们可以实力地打一个表
/*********************************** * * * Auther Rhapsody * * E-mail [email protected] * * * ***********************************/ #include <set> #include <map> #include <cmath> #include <deque> #include <queue> #include <vector> #include <cstdio> #include <cstdlib> #include <cstring> #include <iostream> #include <algorithm> #define MP make_pair #define PB push_back using namespace std; typedef long long LL; typedef pair<int, int> PII; const int N = 5e6 + 7; const int INF = 0x3f3f3f3f; int MOD = 1e9 + 7; int f[N]; //map <PII, int> Mapper; int pow_mod(int x, int y, int MOD) { int Ans = 1; while (y) { if (y & 1) Ans = (LL)Ans * x % MOD; x = (LL)x * x % MOD; y >>= 1; } return Ans; } int find(int a, int idx, int MOD) { int x = pow_mod(2, a, MOD); x = (x + 1 - idx) % MOD; x = (x + MOD) % MOD; return idx - MOD + x; } int main(void) { int T, Test = 0; scanf("%d", &T); int a, m; while (T--) { scanf("%d%d", &a, &m); MOD = m; //Mapper.clear(); f[0] = 2 % MOD; f[1] = 10 % MOD; //Mapper[MP(f[1], f[0])] = 1; int idx = 2, loop, S; while (true) { f[idx] = (f[idx - 1] * 10 - f[idx - 2]) % MOD; f[idx] = (f[idx] + MOD) % MOD; //PII t = MP(f[idx], f[idx - 1]); if (f[idx] != f[1] || f[idx - 1] != f[0]) { //Mapper[t] = idx++; ++idx; continue; } S = idx; loop = idx - 1; break; } int sum = 1; bool flag = true; for (int i = 1; i <= a; ++i) { sum = sum * 2; if (sum + 1 > S) { flag = false; break; } } if (flag) { printf("Case #%d: %d\n", ++Test, (f[sum + 1] - 1 + MOD) % MOD); continue; } printf("Case #%d: %d\n", ++Test, (f[find(a, S, loop)] - 1 + MOD) % MOD); } return 0; }
时间: 2024-11-06 13:01:55