zoukankan      html  css  js  c++  java
  • 某不知出处的题,前缀和后缀和预处理

    Description:

    给出数列A1,A2,...,AN,并设

    Bi = (A1 * A2 * A3 ... AN) / Ai mod (109 + 7)

    现要求把所有的Bi 算出来

    Input:

    输入包含多组测试数据。对于每组数据,第1 行,1 个整数N(1 ≤N ≤100,000), 表示数列的长度。第2

    行,N 个整数A1,A2,...,AN(1 ≤Ai≤109),表示给出的数列。输入以一个 0 表示结尾。

    Output:

    对于每组数据,输出一行,N 个整数用空格分隔,表示算出的B1,B2,...,BN。

    Sample Input:

    3

    1 2 3

    0

    Sample Output:

    6

    3

    2

        题意:说的很详细了里面。我找不到原题。。。好多博主写过这个,但是都没有贴地址,所以我也没发帖,见谅哈。

        解析:看数据,ai过大,直接乘就溢出了。使用(a*b)%c==(a%c*b%c)%c。我们可以直接这么处理,乘起来。但问题是,对于乘法,有模分配律,但是除法没有。那么问题来了,对于题意来讲,bi=(a1*a2....*an)/ai mod,来讲,直接乘的时候不算ai,约掉不就好了?不行,因为n的数据,n*n不行。所以引入前缀积和后缀积来处理。举个例子,b2=(a1*a2*a3*a4)/a2  %mod。。

           原式就是b2=(a1*a3*a4)%mod==(a1%mod*(a3*a4)%mod)%mod。这里的a1,是i=2往前的前缀积,a3*a4是i=2之后的后缀积。那么显而易见,前缀和与后缀和在这里面处理的很巧妙。

    #include<iostream>
    #include<vector>
    #include<set>
    #include<cmath>
    using namespace std;    
    typedef long long ll;
    const int maxn=1e5+10;
    const int mod=1000000007;
    ll a[maxn],l[maxn],r[maxn];
    int main()
    {
        int n;
        while(scanf("%d",&n)&&n)
        {
            for(int i=1;i<=n;i++)
            {
                scanf("%lld",&a[i]);
            }
            l[0]=1;
            r[n+1]=1;
            for(int i=1;i<=n;i++)
                l[i]=(a[i]*l[i-1])%mod;
            for(int i=n;i>=1;i--)
                r[i]=(a[i]*r[i+1])%mod;
            for(int i=1;i<=n;i++)
            {
                printf("%lld
    ",(l[i-1]*r[i+1])%mod);
            }
        }
    }
  • 相关阅读:
    C++快速排序
    C++冒泡排序
    为什么Excel创建一个新的工作簿就会初始化三个worksheet
    为什么游戏需要英雄
    2015.11.18——Lua中文教程
    [国家集训队2012]JZPFAR
    后缀数组小结?
    [BZOJ 2738]矩阵乘法
    [BZOJ 3221][Codechef FEB13] Obserbing the tree树上询问
    [BZOJ 4999]This Problem Is Too Simple!
  • 原文地址:https://www.cnblogs.com/liyexin/p/12517952.html
Copyright © 2011-2022 走看看