一、(算法)求集合中数字组合相加最接近目标数并且大于的组合
1、比如集合中的数字为【888,9,5,777,33,18,22,345,55,1233】,需要接近的数字为 3372
这时需要匹配出来的一组组合为【1233,888, 777,345,55, 33, 22, 18,5】
Stock stock1 = new Stock();
stock1.setId(1);
stock1.setNum(9);
Stock stock2 = new Stock();
stock2.setId(2);
stock2.setNum(5);
Stock stock3 = new Stock();
stock3.setId(3);
stock3.setNum(18);
Stock stock4 = new Stock();
stock4.setId(4);
stock4.setNum(22);
Stock stock5 = new Stock();
stock5.setId(5);
stock5.setNum(33);
Stock stock6 = new Stock();
stock6.setId(1);
stock6.setNum(55);
Stock stock7 = new Stock();
stock7.setId(2);
stock7.setNum(345);
Stock stock8 = new Stock();
stock8.setId(3);
stock8.setNum(777);
Stock stock9 = new Stock();
stock9.setId(4);
stock9.setNum(888);
Stock stock10 = new Stock();
stock10.setId(5);
stock10.setNum(1233);
List<Stock> list = new ArrayList<>();
list.add(stock1);
list.add(stock2);
list.add(stock3);
list.add(stock4);
list.add(stock5);
list.add(stock6);
list.add(stock7);
list.add(stock8);
list.add(stock9);
list.add(stock10);
double ck = 3372; //匹配的数字
2、先对集合按从小到大的顺序排好
list = list.stream().sorted(Comparator.comparing(Stock::getNum)).collect(Collectors.toList());
3、如果匹配的数字大于全部数字总数,我们就直接剔除
//对集合中的全部数字进行累加
double sumNum = list.stream().mapToDouble(Stock::getNum).sum();
if(sumNum < ck){
System.out.println("数量不足");
return;
}
4、现在就直接对集合中的数字进行匹配就可以了
int i = 0;
while (ck != 0){
//当匹配的数字减去集合中最大的数字还大于0的时候,则继续执行
if (ck - list.get(list.size()-1).getNum() > 0){
System.out.println("+"+list.get(list.size()-1).getNum());
ck = ck - list.get(list.size()-1).getNum();
//将已经匹配过的数字从集合中除去
list.remove(list.get(list.size()-1));
}else{
//当匹配的数字减去集合中最小的数字还小于或者等于0的时候,说明已经够了,就直接break退出循环
if (list.get(i).getNum() - ck >= 0){
System.out.println("+"+list.get(i).getNum());
list.get(i).setNum(list.get(i).getNum() - ck);
ck = 0;
break;
}
//如果匹配的数字减去集合中最小的数字还大于0的时候,我们就再次循环,获取第二个最小的数字,依次匹配,直到进入上一个if之中
i++;
}
}