ACdreamoj 1417 思维题

http://115.28.76.232/contest?cid=1128#problem-E

Problem Description

      Consider numbers from 1 to n.
      You have to find the smallest  lexicographically number among them which is divisible by k.

Input

      Input file contains several test cases. Each test case consists of two integer numbers n and k on a line(1 ≤ n ≤ 1018, 1 ≤ k ≤ n).

      The last test case is followed by a line that contains two zeroes. This line must not be processed.

Output

      For each test case output one integer number — the smallest lexicographically number not exceeding n which is divisible by k.

Sample Input

2000 17
2000 20
2000 22
0 0

Sample Output

1003
100
1012
解题思路:

               找到n和m的位数x和y,找到位数分别为 y+1~x 的最小的一个满足%k==0的数,然后和k~10^y+1之间所有满足的数作比较,保留字典序最小的就好了。

/*
* this code is made by life4711
* Problem: 1417
* Verdict: Accepted
* Submission Date: 2014-10-04 15:32:42
* Time: 24MS
* Memory: 1676KB
*/
#include <stdio.h>
#include <iostream>
#include <string.h>
#include <algorithm>
using namespace std;
 
typedef long long LL;
 
LL n,k,flag;
char c[25],s[25],st[25];
 
int main()
{
    while(~scanf("%lld%lld",&n,&k))
    {
        if(n==0&&k==0)
            break;
        LL x=1;
        LL y=1;
        flag=0;
        while(x<n)
        {
            if(x*10>k&&flag==0)
            {
                flag=1;
                y=x*10;
            }
            x*=10;
        }
        //printf("%lld %lld\n",x,y);
        st[0]='9'+1;
        LL t,i;
        flag=-1;
        while(x>=k)
        {
            if(x%k!=0)
                t=k-x%k;
            else
                t=0;
            if(t+x>n)
            {
                x/=10;
                continue;
            }
            //printf("x,t:[%d,%d]\n",x,t);
            flag=t+x;
            if(flag!=-1)
            {
                t=0;
                while(flag>0)
                {
                    s[t++]=flag%10+'0';
                    flag/=10;
                }
                s[t]=0;
                for(int i=0; i<t; i++)
                    c[i]=s[t-1-i];
                c[t]=0;
                //printf("%s\n%s\n",s,c);
                if(strcmp(st,c)>0)
                    strcpy(st,c);
            }
            x/=10;
        }
        for(LL i=k;i<y&&i<=n;i+=k)
        {
 
          // printf("草泥马\n");
            if(i%k==0)
            {
                flag=i;
                t=0;
                while(flag>0)
                {
                    s[t++]=flag%10+'0';
                    flag/=10;
                }
                s[t]=0;
                for(int j=0; j<t; j++)
                    c[j]=s[t-1-j];
                c[t]=0;
                //printf("%s\n%s\n",s,c);
                if(strcmp(st,c)>0)
                    strcpy(st,c);
            }
        }
        printf("%s\n",st);
    }
    return 0;
}
/*
100002150155 1000000001
 
1000 100
 
1254 12
 
13535 2165
 
2163516 3216
 
32135 21321
 
125 120
 
*/


你可能感兴趣的:(ACdreamoj 1417 思维题)