zoukankan      html  css  js  c++  java
  • Podzielno

    问题 B: Podzielno

    时间限制: 1 Sec  内存限制: 128 MB
    提交: 97  解决: 31
    [提交] [状态] [讨论版] [命题人:admin]

    题目描述

    B进制数,每个数字i(i=0,1,...,B-1)有a[i]个。你要用这些数字组成一个最大的B进制数X(不能有前导零,不需要用完所有数字),使得X是B-1的倍数。q次询问,每次询问X在B进制下的第k位数字是什么(最低位是第0位)。

    输入

    第一行包含两个正整数B(2<=B<=10^6),q(1<=q<=10^5)。
    第二行包含B个正整数a[0],a[1],a[2],...,a[B-1](1<=a[i]<=10^6)。
    接下来q行,每行一个整数k(0<=k<=10^18),表示一个询问。

    输出

    输出q行,每行一个整数,依次回答每个询问,如果那一位不存在,请输出-1。

    样例输入

    3 3
    1 1 1
    0
    1
    2
    

    样例输出

    0
    2
    -1
    

    问题

      中文题意 不做解释

    分析

      有一个结论,就是一个数能被B-1整除当且仅当这个数在B进制下的每一位的和能被B-1整除。
      

      证明:
      当一个数的某一位+1时,若进位,则这一位要减去B-1,下一位要+1,则总的贡献是+1.
      当一个数的某一位-1时,若退位,则这一位要加上B-1,下一位要-1,则总的贡献是-1.
      于是当一个数加上B-1时,它在B进制下每一位的总和对B-1取模的值是不变的。
      要是B-1的倍数,那么各位之和对B-1取余一定是零。

        a*Bk≡a (mod (B-1) )
       

      因为要求最大的B进制数,所以贪心每个数都占一位,对B-1取余,减去一个余数。

      所以求一个前缀和,lower_bound求值就可以了。

      

    ///  author:Kissheart  ///
    #include<stdio.h>
    #include<algorithm>
    #include<iostream>
    #include<string.h>
    #include<vector>
    #include<stdlib.h>
    #include<math.h>
    #include<queue>
    #include<deque>
    #include<ctype.h>
    #include<map>
    #include<set>
    #include<stack>
    #include<string>
    #define INF 0x3f3f3f3f
    #define FAST_IO ios::sync_with_stdio(false)
    const double PI = acos(-1.0);
    const double eps = 1e-6;
    const int MAX=1e6+10;
    const int mod=1e9+7;
    typedef long long ll;
    using namespace std;
    #define gcd(a,b) __gcd(a,b)
    inline ll lcm(ll a,ll b){return a/gcd(a,b)*b;}
    inline ll qpow(ll a,ll b){ll r=1,t=a; while(b){if(b&1)r=(r*t)%mod;b>>=1;t=(t*t)%mod;}return r;}
    inline ll inv1(ll b){return qpow(b,mod-2);}
    inline ll exgcd(ll a,ll b,ll &x,ll &y){if(!b){x=1;y=0;return a;}ll r=exgcd(b,a%b,y,x);y-=(a/b)*x;return r;}
    inline ll read(){ll x=0,f=1;char c=getchar();for(;!isdigit(c);c=getchar()) if(c=='-') f=-1;for(;isdigit(c);c=getchar()) x=x*10+c-'0';return x*f;}
    //freopen( "in.txt" , "r" , stdin );
    //freopen( "data.txt" , "w" , stdout );
    ll B,k,q;
    ll a[MAX],sum[MAX];
    ll s,p;
    int main()
    {
        scanf("%lld%lld",&B,&q);
        p=B-1;
        for(ll i=0;i<B;i++)
        {
            scanf("%lld",&a[i]);
            s=(s+i*a[i])%p;
        }
        if(s) a[s]--;
        sum[0]=a[0];
        for(ll i=1;i<B;i++) sum[i]=sum[i-1]+a[i];
        while(q--)
        {
            scanf("%lld",&k);
            if(k+1>sum[B-1])
                printf("-1
    ");
            else
            {
                ll pos;
                pos=lower_bound(sum,sum+B,k+1)-sum;
                printf("%lld
    ",pos);
            }
        }
        return 0;
    }
    View Code
  • 相关阅读:
    I/O会一直占用CPU吗?【转载】
    CPU和线程的关系
    future封装了callable,thread封装future。
    (转)Java中的守护线程
    线程中sleep方法和wait方法有什么区别?(转)
    Java异常---获取异常的堆栈信息
    分析iOS Crash文件,使用命令符号化iOS Crash文件
    String Matching(poj1580)
    U转串口驱动安装
    [LNU.Machine Learning.Question.1]梯度下降方法的一些理解
  • 原文地址:https://www.cnblogs.com/Kissheart/p/10116693.html
Copyright © 2011-2022 走看看