数学题

也许更好的阅读体验

\(\mathcal{Description}\)

\(n,b,k\),求
\(\begin{aligned}\sum_{i=1}^n\begin{pmatrix}i\\k \end{pmatrix}b^i\end{aligned}\)

答案对\(998244353\)取模

\(1\leq k\leq 500000,1\leq n\leq 10^{18},2\leq b\leq 998244353\)

\(\mathcal{Solution}\)


\(\begin{aligned}f_{k}=\sum ^{n}_{i=1}\begin{pmatrix} i \\ k \end{pmatrix}b^{i}\end{aligned}\)
则有
\(\begin{aligned}f_{k-1}=\sum ^{n}_{i=1}\begin{pmatrix} i \\ k-1 \end{pmatrix}b^{i}\end{aligned}\)

\(\begin{aligned}bf_{k}=\sum ^{n+1}_{i=2}\begin{pmatrix} i-1 \\ k \end{pmatrix}b^{i}\end{aligned}\)

\(\begin{aligned}bf_{k-1}=\sum ^{n+1}_{i=2}\begin{pmatrix} i-1 \\ k-1 \end{pmatrix}b^{i}\end{aligned}\)

\(\begin{aligned}bf_{k}+bf_{k-1}=\sum ^{n+1}_{i=2}\left(\begin{pmatrix} i-1 \\ k \end{pmatrix}+\begin{pmatrix} i-1 \\ k-1 \end{pmatrix}\right)b^{i}=\sum ^{n+1}_{i=2}\begin{pmatrix} i \\ k \end{pmatrix}b^{i}=f_k+\begin{pmatrix}n+1\\ k\end{pmatrix}b^{n+1}-\begin{pmatrix}1\\k\end{pmatrix}b\end{aligned}\)

移项得

\(\left(b-1\right)f_k=\begin{pmatrix}n+1\\k\end{pmatrix}b^{n+1}-\begin{pmatrix}1\\k\end{pmatrix}b-bf_{k-1}\)

\(f_k=\dfrac{\begin{pmatrix}n+1\\k\end{pmatrix}b^{n+1}-\begin{pmatrix}1\\k\end{pmatrix}b-bf_{k-1}}{b-1}\)

\(k=0\)时,要求的就是一个等比数列,我们用等比数列求和公式直接算就可以了

\(f_0=\dfrac{b^{n+1}-b}{b-1}\)

总复杂度\(O(k)\)

\(\mathcal{Code}\)

/*******************************
Author:Morning_Glory
LANG:C++
Created Time:2019年09月17日 星期二 10时54分50秒
*******************************/
#include <cstdio>
#include <fstream>
#define ll long long
using namespace std;
const int mod = 998244353;
const int maxn = 500005;
ll n,b,k,ans;
ll invb,mi,C;
ll inv[maxn];
//{{{ksm
ll ksm (ll a,ll b)
{
    a%=mod;
    ll s=1;
    for (;b;b>>=1,a=a*a%mod)
        if (b&1)    s=s*a%mod;
    return s;
}
//}}}
int main()
{
    scanf("%lld%lld%lld",&n,&b,&k);
    C=(n+1)%mod,inv[1]=1,invb=ksm(b-1,mod-2);
    for (int i=2;i<=k;++i)  inv[i]=(-mod/i*inv[mod%i]%mod+mod)%mod;
    ans=(ksm(b,n+1)-b+mod)%mod*invb%mod;
    mi=ksm(b,n+1);
    if (n<k){   printf("0\n");return 0;}
    if (n==k){  printf("%lld\n",ksm(b,n));return 0;}
    for (int i=1;i<=k;++i){
        ll t=0;
        if (i<=1)   t=b;
        ans=((C*mi%mod-t-b*ans%mod)%mod+mod)%mod*invb%mod;
        C=(n-i+1)%mod*C%mod*inv[i+1]%mod;
    }
    printf("%lld\n",ans);
    return 0;
}

如有哪里讲得不是很明白或是有错误,欢迎指正
如您喜欢的话不妨点个赞收藏一下吧

转载于:https://www.cnblogs.com/Morning-Glory/p/11536917.html

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值