前往小程序,Get更优阅读体验!
立即前往
首页
学习
活动
专区
工具
TVP
发布
社区首页 >专栏 >【CodeForces 520E】Pluses everywhere

【CodeForces 520E】Pluses everywhere

作者头像
饶文津
发布2020-06-02 15:25:27
3330
发布2020-06-02 15:25:27
举报
文章被收录于专栏:饶文津的专栏饶文津的专栏

n个数里插入k个+号,所有式子的和是多少(取模1000000007) (0 ≤ k < n ≤ 105)。

分析

1.求答案,考虑每个数作为i位数(可为答案贡献10的i-1次方,个位i=1,十位i=2,...,最多n-k位):

那么它及后面 共i个数 之间不能有加号。

且只有前n-i+1个数可以作为i位,如果是an-i+1作为i位,那么后面都不能有加号,k个加号在a1到an-i+1之间,所以有C(n-i,k)次贡献(这么说怪怪的→_←),就是几种情况。

a1 a2 a3 ... an-i+1 ... an

如果是a1、a2、...an-i作为i位,比如a1,那就是ai和ai+1之间用掉一个加号,其它加号ai+1的后面n-1-i个间隔里。

a1 a2 a3 ... ai + ai+1 ...  an

再比如a2,剩下k-1个加号在ai+2的后面及a1和a2之间 n-1-i个间隔里。

a1 a2 a3 ... ai+1 + ai+2 ...  an

所以他们都做了C(n-i-1,k-1)次贡献。

于是就有ans=∑(i=1到n-k)[(a1+a2+...an-i)*C(n-i-1,k-1)+an-i+1*C(n-i,k)]%M。

s[i]为前缀和,ans=∑(i=1到n-k)[s[n-i]*C(n-i-1,k-1)+an-i+1*C(n-i,k)]%M。

2.组合数取模

由费马小定理,当a和p互质时:ap-1≡1 mod p 可得 a*ap-2≡1 mod p,ap-2和a互为逆元。

a/b mod p=a*b-1 mod p 也就是求除数的逆元。

C(a,b)=a!/[b!*(a-b)!]

所以先求出所有1到n的阶乘,和它的逆。

代码

代码语言:javascript
复制
#include<cstdio>
#define M 1000000007
#define N 100005
#define ll long long

int n,k;
char d[N];
ll s[N],fac[N],inv_fac[N];
ll inv(ll a)
{
    ll b=M-2;
    ll ans=1;
    while(b)
    {
        if(b&1) ans=ans*a%M;
        a=a*a%M;
        b>>=1;
    }
    return ans;
}
void init()
{
//初始化fac[i]i的阶乘,inv_fac[i] i的阶乘的逆元
    fac[0]=1;
    for(int i=1; i<=n; i++)
    {
        fac[i]=fac[i-1]*i;
        if(fac[i]>=M) fac[i]%=M;
    }
    inv_fac[n]=inv(fac[n]);
    for(int i=n-1;i>=0;i--){

//乘(i!的逆)==除以i!==除以(i+1)!再乘以(i+1)==乘((i+1)!的逆)再乘以i+1
        inv_fac[i]=inv_fac[i+1]*(i+1);
        if(inv_fac[i]>=M) inv_fac[i]%=M;
    }
}

ll C(ll a,ll b)
{
    return fac[a]*inv_fac[b]%M *inv_fac[a-b]%M;
}
int main()
{
    scanf("%d%d ",&n,&k);
    for(int i=1; i<=n; i++)
    {
        scanf("%c",&d[i]);
        s[i]=s[i-1]+(d[i]-'0');
    }
    init();
    ll ans=0;
    ll de=1;
    for(ll i=1; n-i>=k; i++)
    {
        ans+=(d[n-i+1]-'0')*C(n-i,k)%M*de%M;
        ans+=s[n-i]*C(n-i-1,k-1)%M*de%M;
        de*=10;
        if (de>=M) de%=M;
        if (ans>=M) ans%=M;
    }
    printf("%I64d",ans);
    return 0;
}
本文参与 腾讯云自媒体分享计划,分享自作者个人站点/博客。
原始发表:2016-02-28 ,如有侵权请联系 cloudcommunity@tencent.com 删除

本文分享自 作者个人站点/博客 前往查看

如有侵权,请联系 cloudcommunity@tencent.com 删除。

本文参与 腾讯云自媒体分享计划  ,欢迎热爱写作的你一起参与!

评论
登录后参与评论
0 条评论
热度
最新
推荐阅读
目录
  • 题意
  • 分析
  • 代码
领券
问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档