[Problem]
[Solution]
Just look at the range of N, and we know that it's about quick power.
Build a matrix of 3 * 3 like this:
10^x | 1 | 1 |
0 | 1 | 1 |
0 | 0 | 1 |
Ans[i] |
i |
1 |
Ans[i + 1] |
i + 1 |
1 |
You need to calculate each 10^x dividually. The time complex is log^2(n)
[Code]
#include <cstdio>
#include <algorithm>
#include <memory.h>
using namespace std;
typedef long long qw;
#ifdef WIN32
#define lld "%I64d"
#else
#define lld "%lld"
#endif
const int matsz = 3;
qw n, mod;
class matrix {
public:
int n;
qw a[matsz][matsz];
matrix() {
memset(a, 0, sizeof(a));
n = matsz;
}
void operator =(matrix x) {
memcpy(a, x. a, sizeof(a));
}
matrix operator *(matrix x) {
matrix s;
for (int i = 0; i < n; i ++)
for (int j = 0; j < n; j ++)
for (int k = 0; k < n; k ++)
(s. a[i][j] += a[i][k] * x. a[k][j]) %= mod;
return s;
}
void print() {
for (int i = 0; i < n; i ++, putchar(10))
for (int j = 0; j < n; j ++)
printf("%5d", (int)a[i][j]);
putchar(10);
}
};
matrix matPow(matrix a, qw n) {
matrix s;
bool f = 1;
for (; n; n >>= 1, a = a * a)
if (n & 1)
(f) ? (s = a, f = 0) : (s = s * a, 0);
return s;
}
int main() {
#ifndef ONLINE_JUDGE
freopen("in.txt", "r", stdin);
#endif
matrix s;
s. a[2][0] = 1;
scanf(lld lld, &n, &mod);
for (qw i = 1, m = 10; i <= n; i *= 10, (m *= 10) %= mod) {
matrix a, r;
a. a[0][0] = m;
a. a[0][1] = 1;
a. a[0][2] = 1;
a. a[1][1] = 1;
a. a[1][2] = 1;
a. a[2][2] = 1;
r = matPow(a, min(i * 10 - 1, n) - i + 1);
s = r * s;
}
printf("%d\n", (int)s. a[0][0]);
}