time limit per test2 seconds
memory limit per test256 megabytes
inputstandard input
outputstandard output
Vasya decided to pass a very large integer n to Kate. First, he wrote that number as a string, then he appended to the right integer k — the number of digits in n.
Magically, all the numbers were shuffled in arbitrary order while this note was passed to Kate. The only thing that Vasya remembers, is a non-empty substring of n (a substring of n is a sequence of consecutive digits of the number n).
Vasya knows that there may be more than one way to restore the number n. Your task is to find the smallest possible initial integer n. Note that decimal representation of number n contained no leading zeroes, except the case the integer n was equal to zero itself (in this case a single digit 0 was used).
Input
The first line of the input contains the string received by Kate. The number of digits in this string does not exceed 1 000 000.
The second line contains the substring of n which Vasya remembers. This string can contain leading zeroes.
It is guaranteed that the input data is correct, and the answer always exists.
Output
Print the smalles integer n which Vasya could pass to Kate.
Examples
input
003512
021
output
30021
input
199966633300
63
output
3036366999
【题解】
怎样从所给的序列中求出原来数字的长度?
比如给的序列长度为93;
则很容易想到实际位数为91,然后最后面加上了数字92,变成长度为93;
又比如103位,则100是实际长度,最后加上数字100,然后就变成103位了。
1004位则,1000位,后面加上1000这个数字占了4位。
然后最多的位数为1000000;
则枚举描述这个数位需要的数字个数i;
设g(x)为某个数字的长度;
所给序列的长度为len;
则
if (g(len-i)==i) ->len-i就是原来的数字的长度;
把len-i这个数字的各个位上的数字在所给的数字中去掉
然后所给的子串是连续的几个数字
也在原数中把它剔除掉;
最后剩下的数字分两类搞;
ans1:找一个最小的非0数字放在最前面。剩下的升序加入。然后在加入的时候判断所给的数字应该放在哪里;
ans2:直接把那个子串放在最前面;剩余的升序放;
ans2可以包括最后答案等0的情况;
当然ans1和ans2也可以合在一起写;
最后输出min(ans1,ans2)即可;
#include <cstdio>
#include <cmath>
#include <iostream>
#include <algorithm>
#include <cstring>
#include <queue>
#include <vector>
#include <stack>
#include <string>
#define LL long long
using namespace std;
const int MAXN = 1000010;
char s1[MAXN], s2[MAXN];
int cnt[10];
void input_ll(LL &r)
{
r = 0;
char t = getchar();
while (!isdigit(t)) t = getchar();
LL sign = 1;
if (t == '-')sign = -1;
while (!isdigit(t)) t = getchar();
while (isdigit(t)) r = r * 10 + t - '0', t = getchar();
r = r*sign;
}
void input_int(int &r)
{
r = 0;
char t = getchar();
while (!isdigit(t)) t = getchar();
int sign = 1;
if (t == '-')sign = -1;
while (!isdigit(t)) t = getchar();
while (isdigit(t)) r = r * 10 + t - '0', t = getchar();
r = r*sign;
}
bool ok(char t,int len)
{
for (int i = 1; i <= len; i++)
if (s2[i] != t)
return t > s2[i];
return false;
}
int main()
{
//freopen("F:\\rush.txt", "r", stdin);
scanf("%s", s1+1);
int len = strlen(s1 + 1);
for (int i = 1; i <= len; i++)
cnt[s1[i] - '0']++;
int nw;
for (int i = 1; i <= 7; i++)
{
int num = len - i;
int tt = 0;
while (num)
{
tt++;
num /= 10;
}
if (tt == i)
{
nw = len-i;
break;
}
}
while (nw)
{
cnt[nw % 10]--;
nw /= 10;
}
scanf("%s", s2 + 1);
len = strlen(s2 + 1);
for (int i = 1; i <= len; i++)
cnt[s2[i] - '0']--;
int findnum = -1;
bool added = false;
string ans1="", ans2="";
ans2 += s2 + 1;
for (int i=1;i <= 9;i++)
if (cnt[i] > 0)
{
ans1 += char(i + '0');
findnum = i;
cnt[i]--;
break;
}
for (int i = 0; i <= 9; i++)
{
char t = i + '0';
if (findnum == i)
ans2 += t;
if (!added && ok(t,len))
{
ans1 += s2 + 1;
added = true;
}
while (cnt[i])
{
ans1 += t;
ans2 += t;
cnt[i]--;
}
}
if (findnum == -1)
puts(ans2.c_str());
else
{
if (!added)
ans1 += s2;
if (ans2[0] == '0')
puts(ans1.c_str());
else
puts(min(ans1, ans2).c_str());
}
return 0;
}