HDU 5744 Keep On Movin
Mean
给定\(n\)个字符,每个字符的数量为\(a_i\),需要你构造出若干组回文串,求所有组合方案中最短长度的最大值。
Sol
贪心
计手上相等对数目为\(num\)
\(a[i]\)为奇数的情况取到剩下1,此时手上的相等对数量加上\(a[i]/2\)。
\(a[i]\)为偶数的情况下全部取完,此时手上的相等对数量加上\(a[i]/2\)。
计\(cnt\)为\(a\)中奇数的个数。
若\(cnt=0\),则答案为\(num*2\)。
否则,将所有对均分给这些奇数个位置,答案为\(2*num/cnt+1\)
Code
#include<bits/stdc++.h>
#define rep(i,a,b) for(int i=(a);i<=(b);++i)
#define dep(i,a,b) for(int i=(a);i>=(b);--i)
#define lowbit(x) (x&(-x))
#define debug(x) cout<<#x<<" :"<<x<<endl
#define debug1(x) cout<<#x<<" :"<<x<<" "
using namespace std;
typedef unsigned long long ull;
typedef long long ll;
const int N=2e5+20;
const int MAX=10000007;
inline int read() {
char c=getchar();int x=0,f=1;
while(c<'0'||c>'9'){if(c=='-')f=-1;c=getchar();}
while(c>='0'&&c<='9'){x=x*10+c-'0',c=getchar();}
return x*f;
}
inline void out(int x) {
if(x>9) out(x/10);
putchar(x%10+'0');
}
int q[N];
int n;
int main(){
int T=read();
while(T--){
n=read();
int sum = 0;
int od = 0;
rep(i,1,n){
q[i]=read();
if(q[i]&1){
od++;
sum+=q[i]/2;
}
else sum+=q[i]/2;
}
if(!od)printf("%d\n",sum*2);
else printf("%d\n",sum/od*2+1);
}
return 0;
}