题意:
给出n个数字,这些数字数由另外n个数字各个位数的和得来的。求另外个数,要尽量小,而且要递增。
题解:
从最小位往最大位贪心,如果可以在做到最小位大于上一个数其他位与上一个数相等最好,不行就再往前面试,全部都不行就要位数比前面的大,具体参见:http://blog.csdn.net/ck_boss/article/details/43573911
#include <cstdio> #include <cstring> #include <vector> #include <algorithm> #include <iostream> #include <map> #include <queue> #include <stack> //#pragma comment(linker, "/STACK:102400000,102400000") using namespace std; #define PF(x) cout << "debug: " << x << " "; #define EL cout << endl; #define PC(x) puts(x); typedef long long ll; #define CLR(x, v) sizeof (x, v, sizeof(x)) using namespace std; const int INF = 0x5f5f5f5f; const int maxn = 350; const int mod = 1e9 + 7; int pos[maxn],num[maxn][maxn],b[maxn],n; int main() { // freopen("in.txt","r",stdin); cin>>n; for(int i = 1;i <= n;i++) scanf("%d",&b[i]); int last = b[1]; while(b[1] >= 9) num[1][++pos[1]] = 9,b[1] -= 9; if(b[1] > 0) num[1][++pos[1]] = b[1]; bool fg = false; b[1] = last; for(int i = 2;i <= n;i++){ fg = false; last = b[i-1]; for(int j = 1;fg == false;j++){ last -= num[i-1][j-1]; for(int k = num[i-1][j] + 1;k <= 9&&fg == false;k++){ int add = k-num[i-1][j]; if(last + add <= b[i]&&last + add +9*(j-1) >= b[i]){ fg = true; int tn = 0; pos[i] = max(pos[i-1],j); int val = b[i] - last - add; while(val > 0){ if(val >= 9){ num[i][++tn] = 9,val -= 9;} else if(val > 0){num[i][++tn] = val,val = 0;} } num[i][j] = k; for(int t = j+1;t <= pos[i];t++) num[i][t] = num[i-1][t]; } } } } for(int i = 1;i <= n;i++){ for(int j = pos[i];j >= 1;j--) printf("%d",num[i][j]); printf(" "); } return 0; }