这次花了三个小时写一个题,期间真的wa到哭,难倒是不难,就是很麻烦,上题
描述
给定一些不同的一位数字,你可以从这些数字中选择若干个,并将它们按一定顺序排列,组成一个整数,把剩下的数字按一定顺序排列,组成另一个整数。组成的整数不能以0开头(除非这个整数只有1位)。
例如,给定6个数字,0,1,2,4,6,7,你可以用它们组成一对数10和2467,当然,还可以组成其他的很多对数,比如210和764,204和176。这些对数中两个数差的绝对值最小的是204和176,为28。
给定N个不同的0~9之间的数字,请你求出用这些数字组成的每对数中,差的绝对值最小的一对(或多对)数的绝对值是多少?
格式
输入格式
第一行包括一个数T(T≤1000),为测试数据的组数。
每组数据包括两行,第一行为一个数N(2≤N≤10),表示数字的个数。下面一行为N个不同的一位数字。
输出格式
T行,每行一个数,表示第i个数据的答案。即最小的差的绝对值。
样例1
样例输入1
2
6
0 1 2 4 6 7
4
1 6 3 4
样例输出1
28
5
提示
友情提示:每个数字出现了偶数次会抵消。
例如2 2 2当作一个2来处理,3 3相当于没有数字。
这个在题目中好象没有说。
来源
某校NOIP模拟题
思路:就是分N=2和N>2(要分奇偶)
输入时要注意把重复的去掉
贪心策略:1、如果是N=2,那么就这两个数相减。
2、如果N>2为偶,选两个不为零的数之差最小分别作为所求两个数的首位,如果出现最小的有多个,全部求出结果之后再求最小值。然后把那两个选出的数都置为-1,这两个选出的数大的要求剩下的位尽可能小,小的剩下的位尽可能大,相减才会更小。
3、如果N>2为奇,选一个不为零的最小的数作为较大的那个数的首位,选最大的数作为较小的那个数的首位,剩下的与2中类似。
AC代码:
#include<bits/stdc++.h>
using namespace std;
bool cmp(int a,int b)
{
return a>b;
}
int Pow(int n)
{
int ans=1;
for(int i=1;i<=n;i++)
ans*=10;
return ans;
}
int main()
{
int T,N,n;
int a[15];
int b[100];
int book[100];
int vis[100];
int c[15];
cin>>T;
while(T--)
{
N=0;
memset(a,0,sizeof a);
memset(book,0,sizeof book);
memset(vis,0,sizeof vis);
cin>>n;
for(int i=1;i<=n;i++)
{
cin>>b[i];
if(!book[b[i]])
{
a[++N]=b[i];
book[b[i]]=1;
}
}
int ans,_min=999999;
sort(a+1,a+N+1);
int u,v;
if(N==2)
{
ans=abs(a[1]-a[2]);
_min=ans;
}
else if(N%2==0)
{
int M=10;
int Min=9999999;
memcpy(c,a,sizeof a);
while(M--)
{
for(int i=1;i<=N;i++)
{
int flag=0;
for(int j=i+1;j<=N;j++)
if(abs(a[i]-a[j])<=Min&&a[i]&&a[j])
{
Min=abs(a[i]-a[j]);
u=i;
v=j;
if(!vis[u])
{
vis[u]=1;
flag=1;
break;
}
}//u<v,a[u]<a[v]
if(flag)
break;
}
int prod=a[v];
int prox=a[u];
a[u]=-1;
a[v]=-1;
sort(a+1,a+N+1);
prod*=Pow(N/2-1);
for(int i=3,k=N/2-2;i<=(N-2)/2+2;i++,k--)
prod+=a[i]*Pow(k);
sort(a+1,a+N+1,cmp);
prox*=Pow(N/2-1);
for(int i=1,k=N/2-2;i<=(N-2)/2;i++,k--)
prox+=a[i]*Pow(k);
ans=prod-prox;
_min=min(ans,_min);
memcpy(a,c,sizeof c);
}
}
else
{
int prod;
for(int i=1;i<=N;i++)
if(a[i])
{
prod=a[u=i];
break;
}
int prox=a[N];
a[u]=-1;
a[N]=-1;
sort(a+1,a+N+1);
prod*=Pow((N-1)/2);
for(int i=3,k=(N-1)/2-1;i<=(N-1)/2+2;i++,k--)
prod+=a[i]*Pow(k);
sort(a+1,a+N+1,cmp);
prox*=Pow((N-1)/2-1);
for(int i=1,k=(N-1)/2-2;i<=(N-1)/2-1;i++,k--)
prox+=a[i]*Pow(k);
ans=prod-prox;
_min=ans;
}
cout<<_min<<endl;
}
return 0;
}