hdu 6198 number number number

来源:互联网 发布:如何更新mac系统 编辑:程序博客网 时间:2024/06/06 08:11

题目:

http://acm.hdu.edu.cn/showproblem.php?pid=6198

题意:

如果一个数字n可以等于k个斐波那契数的和(这些斐波那契数可以相等),那么n就称为mifgood,否则就是mifbad,当给定k时,求最小mifbad数字

思路:

可以推出规律,当k=1时,答案为4,当k=2时,可以发现,当首次遇到相邻两个fib数字ai, ai+1之差大于4时,那么第一个mifbad就一定是ai+4,因为ai+1,ai+2,ai+3都是可以凑出来的,可以发现答案是8+4=12;当k=3时,首次遇到相邻两个fib数字ai,ai+1之差大于12时,那么ai+12是一定凑不出来的,答案就是21+12=33…一直推下去,可以发现4=5112=13133=34188=891…答案就是fib(4+2k1)1,用矩阵快速幂求解

#include <bits/stdc++.h>using namespace std;typedef long long ll;const int N = 10 + 10;const ll mod = 998244353;struct matrix{    int row, col;    ll mat[N][N];    matrix(int _row=0, int _col=0)    {        init(_row, _col);    }    void init(int _row, int _col)    {        row = _row, col = _col;        memset(mat, 0, sizeof mat);    }    matrix operator* (matrix b)    {        matrix c(row, b.col);        for(int i = 1; i <= row; i++)            for(int j = 1; j <= b.col; j++)                for(int k = 1; k <= col; k++)                    c.mat[i][j] = (c.mat[i][j] + mat[i][k] * b.mat[k][j] % mod) % mod;        return c;    }};matrix mod_pow(matrix a, ll b, ll p){    matrix ans(2, 2);    ans.mat[1][1] = ans.mat[2][2] = 1;    while(b)    {        if(b & 1) ans = ans * a;        a = a * a;        b >>= 1;    }    return ans;}int main(){    int k;    while(~ scanf("%d", &k))    {        k = 4 + 2*k - 1;        matrix a(2, 2);        a.mat[1][1] = 1, a.mat[1][2] = 1;        a.mat[2][1] = 1, a.mat[2][2] = 0;        a = mod_pow(a, k, mod);        printf("%lld\n", a.mat[1][2] - 1);    }    return 0;}
原创粉丝点击