1038 Recover the Smallest Number (30 分)
Given a collection of number segments, you are supposed to recover the smallest number from them. For example, given { 32, 321, 3214, 0229, 87 }, we can recover many numbers such like 32-321-3214-0229-87 or 0229-32-87-321-3214 with respect to different orders of combinations of these segments, and the smallest number is 0229-321-3214-32-87.
Input Specification:
Each input file contains one test case. Each case gives a positive integer N (≤104) followed by N number segments. Each segment contains a non-negative integer of no more than 8 digits. All the numbers in a line are separated by a space.
Output Specification:
For each test case, print the smallest number in one line. Notice that the first digit must not be zero.
Sample Input:
5 32 321 3214 0229 87
Sample Output:
22932132143287
解析:题意就不讲了。这题真的搞了好久,后面实在想不到点上,看了网上的解析“一点即通”,网上的大佬还说这是一道面试的题目,只是改动了。题目中要求组成的数要最小,有若a+b<b+a;说明a在b前面是比较小的,我们给个符号“<<”定义,a<<b是a恒小于b,"<<"有递推性,a<<b,b<<c,则a<<c;
这样直接就一个排序解决了问题。
坑点:样例
1.0000 1111
2.0000 0000
注意处理上面的两个样例
#include<bits/stdc++.h>
using namespace std;
#define ee exp(1)
#define p acos(-1)
#define mod 1000000007
#define inf 0x3f3f3f3f
#define ll long long
#define ull unsigned long long
#define mem(a,b) memset(a,b,sizeof(a))
int gcd(int a,int b){return b?gcd(b,a%b):a;}
string a[10005];
int cmp(string x,string y)
{
return x+y<y+x;
}
int main()
{
int n;cin>>n;
for(int i=0; i<n; i++)
{
cin>>a[i];
}
sort(a,a+n,cmp);
bool flag=true;
for(int i=0; i<n; i++)
{
if(i==0)
{
for(int j=0; j<a[0].size(); j++)
if(a[0][j]=='0'&&flag)continue;
else flag=false,cout<<a[0][j];
}
else
{
if(flag)
{
for(int j=0; j<a[i].size(); j++)
if(a[i][j]=='0'&&flag)continue;
else flag=false,cout<<a[i][j];
}
else cout<<a[i];
}
}
if(flag)
puts("0");
return 0;
}