1982: D.房间安排
时间限制: 2 Sec 内存限制: 256 MB提交: 243 解决: 30
[ 提交][ 状态][ 讨论版]
题目描述
Alice所在的社团计划一次外出游玩。Alice需要安排所有人入住的房间。社团一共订了n个房间,然后Alice给第i间房间安排了ai(0<=ai<=4)个人。向旅馆提交了住宿信息之后,Alice发现如果出现一个房间人数为1或者为2的情况,这个房间的社员就会感觉到孤独和凄凉,会很失望。所以Alice现在想调整一下,把某些社员调到其他房间,使得所有社员都不会感到孤独。但是为了避免不必要的麻烦,她希望调整的人数最少。Alice向Bob求助,Bob希望你能写个程序求出最少需要调整的人数。
注意:你可以把一个房间的初始人员都调出去,允许房间空闲,不允许某个房间人数超过4个。
输入
第一行输入一个整数n(1<=n<=1000000),表示预定的房间数量。
接下来一行输入n个数,第i个数是ai(0<=ai<=4),表示第i个房间初始有ai个人。
输出
输出一个数,表示最少需要调整的人的数量,如果无论怎么安排都不能满足要求,输出-1。
样例输入
51 2 2 4 340 3 0 4
样例输出
20
提示
第一个样例最少需要调动2个人,将第一个房间的一个人调到第二个房间,从第四个房间调一个人到第三个房间,最后人数为0 3 3 3 3,满足要求。
第二个样例不需要调动,所以答案是0
来源
当时做了两个多小时,硬是没做出来,回来继续按着思路写,然后就ok了。
思路:
1,2,3,4的房间分别记录下来,当1等于2的时候,正好完全补上,当1大于2时,按照剩下的1自己组成3,然后余下的一个1或者2个1分别讨论,当1小于2时,剩下的2正好3个2需要移动两个,余下1个2或者两个2分别讨论即可。
#include<iostream>
#include<cstring>
using namespace std;
int a[1000050];
int main()
{
long long n;
while(cin>>n)
{
long long more[5],cnt=0;
memset(more,0,sizeof(more));
for(long long i=1;i<=n;i++)
{
cin>>a[i];
more[a[i]]++;
}
for(int i=1;i<=4;i++)
{
cnt+=more[i]*i;
}
if(cnt<3||cnt==5)
{
cout<<"-1"<<endl;
continue;
}
if(more[1]==more[2])
{
cout<<more[1]<<endl;
continue;
}
else
{
if(more[1]>more[2])
{
int temp=more[2];
int t=more[1]-more[2];
temp+=t/3*2;
if(t%3==1)
{
if(more[3]+more[2]+t/3>=1)
temp++;
else
{
if(more[4]>=2)
{
temp+=2;
}
else
{
cout<<"-1"<<endl;
continue;
}
}
}
if(t%3==2)
{
if(more[4]>=1)
{
temp+=2;
}
else
{
if(more[3]+t/3+more[2]>=2)
{
temp+=2;
}
else
{
cout<<"-1"<<endl;
continue;
}
}
}
cout<<temp<<endl;
continue;
}
if(more[1]<more[2])
{
int temp=more[1];
int t=more[2]-more[1];
temp+=t/3*2;
if(t%3==1)
{
if(more[4]>=1)
temp++;
else
{
if(more[3]+more[2]+t/3>=2)
{
temp+=2;
}
else
{
cout<<"-1"<<endl;
continue;
}
}
}
if(t%3==2)
{
temp+=2;
}
cout<<temp<<endl;
continue;
}
}
}
return 0;
}