题目描述:A想要拿一个左右手颜色相同的手套,现在左右手套分开放置,但现在天黑看不到,问至少要拿多少只手套(左手加右手),才能保证一定能选出一双颜色相同的手套。
输入:n颜色种数(1≤n≤13) 两个长度为n的数组left,right,分别代表每种颜色左右手手套的数量。数据保证左右的手套总数均不超过26,且一定存在至少一种合法方案。
测试用例:
4 , [0,7,1,6] , [1,5,0,6]
返回:10 (解释:可以左手手套取2只,右手手套取8只)
思路:
1、左边至少覆盖所有颜色(对应右边为0时的颜色,要都算在内),右边除了对应左边为0的颜色中至少选择一个。
2、右边至少覆盖所有颜色(对应左边为0时的颜色,要都算在内),左边除了对应右边为0的颜色中至少选择一个。
从两种中选择较少的一个。
代码:
import java.util.*;
public class Gloves {
public int findMinimum(int n, int[] left, int[] right) {
if(n==1){
return 2;
}
// max 表示覆盖所有颜色的数量
// min 表示左右至少有一种重合颜色的数量
int leftMin = countMin(n,left,right);
int rightMin = countMin(n,right,left);
int leftMax = countMax(n,left);
int rightMax = countMax(n,right);
int a = leftMin+rightMax;
int b = leftMax+rightMin;
return a>b?b:a;
}
public int countMin(int n, int[] arr, int[] arr1){
int ret = 0;
for(int i=0;i<n;i++){
if(arr1[i] == 0){
ret += arr[i];
}
}
return ret+1;
}
public int countMax(int n, int[] arr){
int ret = 0;
Arrays.sort(arr);
int countZero = 0;
while(arr[countZero]==0){
countZero++;
}//这里的countZero 是计算了Zero的个数,同时也能确定加到哪里结束,到哪里可以加1就行
for(int i=n-1;i>=countZero;i--){
if(i==countZero+1 && countZero+1<n-1){
ret+=1;
}else{
ret+=arr[i];
}
}
return ret;
}
}
注意事项 :
1. 要注意当只存在一种颜色的时候,左右两边各取一个就行。
2. 要先计算 Min 再计算 Max ,因为Max里面的排序会影响Min的结果。
3. 计算Max,注意是减去除0之外倒数第二小的数字,其他数字和加一,比如 0 1 5 6 的max是 8