题意:
给定船的最大载重量和旅客人数,以及每个旅客的体重,每条船最多坐两人,求让每个旅客都上船所需船数量的最小值。
由于旅客体重范围较小,可直接遍历所有可能的体重,省去了对旅客体重值的排序。用一个数组记录每个体重旅客的人数,根据较轻体重的旅客与较重体重旅客的最佳搭配得到最优解。
代码:
#include<iostream>#include<cstring>
using namespace std ;
int main(){
int a[300] ;
int m, n, i, j ;
cin >> m >> n ;
memset(a, 0, sizeof(a)) ;
int min = 10000, max = -1 ;
for(i=1; i<=n; i++){
cin >> j ;
a[j] ++ ;
if(j<min) min = j ;
if(j>max) max = j ;
}
j = m - min ; //j为最重的旅客
i = min ; //i为最轻的旅客
int msum = 0 ;
while(i<=max){
if(2*i<=m){
if(m-i<j) j = m - i ; //按递减搜索较重旅客
while(a[j]==0) j -- ; //略去不存在的重量
if(j==i){
msum += (a[i] + 1) / 2 ;//若为奇数个,则有一人独坐一船
a[i] = 0 ;
}
else{ //i,j不等,则在i, j中找个数小的那个,组成min个双人对上船,同时i,j的个数分别减min
int k = a[i]>a[j]?a[j]:a[i] ;
msum += k ;
a[i] -= k ;
a[j] -= k ;
}
}
else{ //若2*i>m,则船上只能坐一人,增加a[i]条船,且将a[i]清零
msum += a[i] ;
a[i] = 0 ;
}
while(i<=max&&a[i]==0) //寻找下一位较轻的旅客
i ++ ;
}
cout << msum ;
return 0 ;
}