F. Kosuke's Sloth

Posted on 2024-10-31 21:14  Capterlliar  阅读(9)  评论(0编辑  收藏  举报

题意:给定n和k,求斐波那契数列里能被k整除的第n个数的下标。

解:有两个结论:

1. 当首次能被k整除的数为第i个数时时,数列中能被i整除,当且仅当其下标为i的倍数。

2. 斐波那契数列中模k的循环节长度不超过6k。

于是就很简单了,在小于6k的数里找出第一个能被k整除的数,然后乘n。

代码:

#include<bits/stdc++.h>
using namespace std;
#define ll long long
#define maxx 600005
#define inf 0x3f3f3f3f
#define mod 1000000007

signed main(){
    int T;
    scanf("%d",&T);
    while(T--){
        ll n,k;
        scanf("%lld%lld",&n,&k);
        if(k==1){
            printf("%lld\n",n%mod);
            continue;
        }
        ll a=1,b=1;
        ll res;
        for(int i=3;i<=k*6;i++){
            ll c=(a+b)%k;
            if(!c){
                res=i;
                break;
            }
            a=b%k;b=c%k;
        }
        printf("%lld\n",((res%mod)*(n%mod))%mod);
    }
    return 0;
}
View Code

 

*证明

1. 

假设第一个能被k整除的数为fib[i],fib[i]=m*k,fib[i+1]=m*k+fib[i-1],fib[i+2]=2*m*k+fib[i-1],...,fib[i+i]=i*m*k+fib[i]*fib[i-1],由于fib[i]和fib[i-1]互质(辗转相除法可得),故fib[2*i]为大于fib[i]的第一个能被k整除的数。

2. 

可见皮萨诺周期

 

 —— For my dearest Lappland.