• Codeforces 1373E


    Description

    题目大意:
    (f(x))为十进制下x每一位上的数字的和。求满足(f(x)+f(x+1)+...+f(x+k)=n)的最小x。

    思路

    由于k特别小(<=9),故x+k至多发生一次进位。x每加1,必有某一位加上1。如果发生进位,那么(f(x))只要额外减去若干个9(进位发生后9变为0,要减去)。
    但是由于不知道加多少会发生进位,所以可以枚举个位是多少,假设是a。如果(a+k)>10,说明发生了进位。
    所以枚举个位a和进位影响的9的个数i。故原式可得

    [(k+1) cdot f(x)+frac{k cdot (k+1)}{2}-9 cdot t cdot i=n ]

    可以求出f(x)。(其中t代表有多少个f(x)发生进位,就要减去多少若干个9)
    由于不知道9的个数上限,所以我枚举200个,可以AC。

    对枚举出来的每个f(x),除了个位,其它低的位要尽可能大,使得高位尽可能小和低,同时要保证进位只能影响到i个9。这个根据f(x)的值贪心构造x就好了。

    #include <iostream>
    #include <cstdio>
    #include <queue>
    #include <algorithm>
    #include <map>
    #include <set>
    #include <vector>
    #include <cstring>
    #include <string>
    #include <stack>
    #include <deque>
    #include <cmath>
    #include <iomanip>
    #include <cctype>
     
    #define endl '
    '
    #define IOS std::ios::sync_with_stdio(0);
    #define FILE freopen("..//data_generator//in.txt","r",stdin),freopen("res.txt","w",stdout)
    #define FI freopen("..//data_generator//in.txt","r",stdin)
    #define FO freopen("res.txt","w",stdout)
    #define pb push_back
    #define mp make_pair
    #define seteps(N) fixed << setprecision(N) 
     
    typedef long long ll;
    using namespace std;
    /*-----------------------------------------------------------------*/
     
    #define INF 0x3f3f3f3f
    const int N = 2e2 + 10;
    const double eps = 1e-8;
     
    string s;
     
    bool build(int fx, int x, int i) {
        s.clear();
        s.push_back(x + '0');
        fx -= x;
        for(int p = 0; p < i - 1; p++) {
            s.push_back('9');
            fx -= 9;
        }
        if(fx < 0) return false;
        if(i && fx > 8) {
            fx -= 8;
            s.push_back('8');
        }
        while(fx > 9) {
            fx -= 9;
            s.push_back('9');
        }
        if(fx) s.push_back(fx + '0');
        reverse(s.begin(), s.end());
        return true;
    }
     
    string smin(const string &s1, const string &s2) {
        if(!s1.size()) return s2;
        if(!s2.size()) return s1;
        if(s1.size() == s2.size()) return s1 < s2 ? s1 : s2;
        return s1.size() < s2.size() ? s1 : s2;
    }
     
    int main() {
        IOS;
        int t;
        cin >> t;
        while(t--) {
            int n, k;
            cin >> n >> k;
            int rn = n;
            n -= (k + 1) * k / 2;
            string ans;
            for(int x = 0; x <= 9; x++) { //枚举个位
                int t = (x + k) / 10 * ((x + k) % 10 + 1);
                for(int i = 1; i <= 200; i++) {
                    if((n + 9 * i * t) % (k + 1)) continue;
                    int fx = (n + 9 * i * t) / (k + 1);
                    if(fx > rn) break;
                    if(x > fx) break;
                    if(!t) {if(!build(fx, x, 0)) break;}
                    else {if(!build(fx, x, i)) break;}
                    
                    ans = smin(ans, s);
                    break;  
                }
                
            }
            if(ans.empty()) cout << -1 << endl;
            else cout << ans << endl;
        }
    }
    
  • 相关阅读:
    决策树详解
    快速排序python实现总结
    机器学习-主干学习路线梳理
    动态规划通用解法总结
    Ubuntu系统下环境安装遇到依赖冲突问题
    学习笔记----C语言的面向对象
    Linux下开发stm32--IDE篇
    Deepin中安装使用好用的字典GoldenDict
    python-参考书
    C语言-转义字符
  • 原文地址:https://www.cnblogs.com/limil/p/13196649.html
Copyright © 2020-2023  润新知