码迷,mamicode.com
首页 > 其他好文 > 详细

2020 Multi-University Training Contest 1 . Fibonacci Sum 水题改编

时间:2020-07-21 23:08:28      阅读:137      评论:0      收藏:0      [点我收藏+]

标签:sign   memset   training   数列   blog   就是   signed   lag   题意   

技术图片

 

题意很简单,就是让你求这个东西,这个时候你发现,原题????

https://blog.csdn.net/acdreamers/article/details/23039571

哦,只是原来写过的哪一题的C是1,这个是1e18. 想都不用想,直接二项式展开,求等比数列的前n项和。

你会得到第i项(一共k项):技术图片

这个时候理所当然的想先用二次剩余求出来那几个用到的东西,a,b,1/sqrt(5)。

1你用快速幂求了一下,一交,tle了。

2 然后发现每个都求快速幂太蠢了,所以又优化优化,优化到除了求分母的逆元需要用到快速幂其他的都可以由上一项推出来,然后再交,又wa了。

3 哦,原来这是等比数列,分母是1-q,如果q是1那不就错了吗?所以特判一下如果q是1,加的就是n*a1,a1是几?你看这个Sn,忽略这个组合数,a1不就和q完全相等吗,是1! 就这样a了。

#include <bits/stdc++.h>
#define ll long long
#define ull unsigned long long
#define met(a, b) memset(a, b, sizeof(a))
#define rep(i, a, b) for(int i = a; i <= b; i++)
#define bep(i, a, b) for(int i = a; i >= b; i--)
#define pb push_back
#define mp make_pair
#define debug cout << "KKK" << endl
#define ls num*2
#define rs num*2+1
#define re return
using namespace std;
const ll mod = 1e9 + 9;
const double PI = acos(-1);
const ll INF = 2e18+1;
const int inf = 1e9+5;
const double eps = 1e-7;
const int maxn = 1e5 + 5;
// 逆元
// sqrt(5) = 383008016;
// a = (1+sqrt(5))/2 = 691504013;
// b = (1-sqrt(5))/2 = 308495997;
// 1/sqrt(5) = 276601605;
ll A = 691504013, B = 308495997;
ll sqrt5 = 383008016, invsqrt5 = 276601605;
ll qsm(ll a, ll n){
    ll res = a%mod, sum = 1;
    while(n){
        if(n&1) sum = (sum*res)%mod;
        res = (res*res)%mod;
        n >>= 1;
    }
    return sum;
}

ll fac[maxn], f[maxn], inv[maxn];
ll C(ll m, ll n){
    if(m < n) return 0;
    if(n == 0 || m == n) return 1;
    return fac[m]*inv[n]%mod*inv[m-n]%mod;
}
void init(){
    fac[1] = 1; 
    f[1] = 1;   
    inv[1] = 1; 
    for(ll i = 2; i <= 100000; i++){
        fac[i] = fac[i-1]*i%mod;
        f[i] = (mod - mod/i)*f[mod%i]%mod;
        inv[i] = inv[i-1]*f[i]%mod;
    }
}

ll sac[maxn], sbc[maxn];
int main(){
    // ios::sync_with_stdio(false);
    // cin.tie(0); cout.tie(0);
    init();
    int t; scanf("%d", &t);
    while(t--){
        ll n, c, k; 
        scanf("%lld%lld%lld", &n,&c,&k);
        // n = 1e18, c = 1e18, k = 1e5;
        ll res = qsm(invsqrt5, k);
        ll ans = 0, flag = -1;
        ll x, y;
        ll ac = qsm(A, c), bc = qsm(B, c);
        sac[0] = 1, sbc[0] = 1;
        sac[1] = ac, sbc[1] = bc;
        rep(i, 1, k){
            sac[i] = sac[i-1]*ac%mod;
            sbc[i] = sbc[i-1]*bc%mod;
        }
        ll acn = qsm(qsm(A, c), n);
        ll bcn = qsm(qsm(B, c), n);
        ll invacn = qsm(acn, mod-2);
        ll invbcn = qsm(bcn, mod-2);
        ll now_acn = qsm(acn, k), now_bcn = 1;
        for(ll i = 0; i <= k; i++){
            flag *= -1;
            ll q = sac[k-i] * sbc[i] % mod;
            if(q == 1){
                q = (n%mod)*C(k, i) % mod;
                ans = (ans + flag*q%mod + mod) % mod; 
            }
            else{
                x = (C(k, i)*sac[k-i]%mod) * sbc[i] % mod;
                x = (1-(now_acn * now_bcn % mod) + mod) % mod * x % mod;
                y = (1 - (sac[k-i] * sbc[i])%mod ) % mod;
                y = qsm(y, mod-2);
                ans = (ans + flag*x*y%mod + mod)%mod;
            }
            now_acn = (now_acn * invacn) % mod;
            now_bcn = (now_bcn * bcn) % mod;
        }
        cout << ans*res%mod << endl;
    }
    return 0;
}

 

2020 Multi-University Training Contest 1 . Fibonacci Sum 水题改编

标签:sign   memset   training   数列   blog   就是   signed   lag   题意   

原文地址:https://www.cnblogs.com/philo-zhou/p/13357136.html

(0)
(0)
   
举报
评论 一句话评论(0
登录后才能评论!
© 2014 mamicode.com 版权所有  联系我们:gaon5@hotmail.com
迷上了代码!