记录编号 |
319891 |
评测结果 |
AAAAAAAAAA |
题目名称 |
[HNOI 2011] 数学作业 |
最终得分 |
100 |
用户昵称 |
sxysxy |
是否通过 |
通过 |
代码语言 |
C++ |
运行时间 |
0.007 s |
提交时间 |
2016-10-11 13:33:35 |
内存使用 |
0.29 MiB |
显示代码纯文本
#include <cstdio>
#include <cstdlib>
#include <cstdarg>
#include <cstring>
#include <list>
#include <queue>
#include <vector>
#include <string>
#include <cmath>
#include <algorithm>
using namespace std;
typedef long long LL;
LL MOD;
struct matrix
{
int r, c; //行 列 (宽 长)
LL a[4][4];
matrix(int sw = 3, int sh = 3)
{
r = sw;
c = sh;
}
void sets(int sw, int sh)
{
r = sw;
c = sh;
}
void std_matrix()
{
zero();
for(int i = 1; i <= 3; i++)
a[i][i] = 1;
}
void zero()
{
memset(a, 0, sizeof(a));
}
matrix operator*(matrix &o)
{
matrix res;
res.sets(r, o.c);
res.zero();
for(int i = 1; i <= res.r; i++)
for(int j = 1; j <= res.c; j++)
for(int k = 1; k <= res.c; k++)
{
res.a[i][j] += (a[i][k]%MOD)*(o.a[k][j]%MOD)%MOD;
res.a[i][j] %= MOD;
}
return res;
}
};
LL ipow(LL base, int exp)
{
LL ans = 1;
while(exp)
{
if(exp & 1)
ans = ans * base;
exp >>= 1;
base *= base;
}
return ans;
}
matrix fast_pow(matrix base, int exp)
{
matrix ans;
ans.std_matrix(); //单位矩阵
while(exp)
{
if(exp & 1)
ans = ans * base;
exp >>= 1;
base = base*base;
}
return ans;
}
matrix mmm;
matrix ans;
void calc(LL t ,LL x)
{
mmm.zero();
mmm.a[1][1] = t%MOD;
mmm.a[1][2] = mmm.a[1][3] = 1;
mmm.a[2][2] = mmm.a[2][3] = 1;
mmm.a[3][3] = 1;
for(LL y = x-t/10+1; y; y>>=1, mmm = mmm*mmm)
if(y&1)
ans = mmm*ans;
//生无可恋的眼神...矩阵乘法不满足交换律之前写ans = ans*mmm无限WA调了1小时..
}
int main()
{
freopen("mathwork.in", "r", stdin);
freopen("mathwork.out", "w", stdout);
LL n;
scanf("%lld %lld", &n, &MOD);
ans.std_matrix();
LL t = 10;
while(n >= t)
{
calc(t, t-1);
t *= 10;
}
calc(t, n);
printf("%lld\n", ans.a[1][3]);
return 0;
}