题目来源:
leetcode题目,网址:LCP 33. 蓄水 - 力扣(LeetCode)
解题思路:
暴力遍历,边界为 1 与 最大最低蓄水量与1之和 。不需要蓄水的情况特殊处理。
解题代码:
class Solution {
public int storeWater(int[] bucket, int[] vat) {
boolean ZeroFlag=true;
int maxPourWater=0;
for(int i=0;i<vat.length;i++){
if(vat[i]!=0){
ZeroFlag=false;
}
if(bucket[i]==0){
maxPourWater=Math.max(vat[i],maxPourWater);
}else{
maxPourWater=Math.max(vat[i]/bucket[i]+1,maxPourWater);
}
}
if(ZeroFlag){
return 0;
}
int res=Integer.MAX_VALUE;
for(int i=0;i<=maxPourWater;i++){
res=Math.min(forMinOperation(bucket,vat,i),res);
}
return res;
}
public int forMinOperation(int[] bucket,int[] vat,int pourWaterTime){
int res=pourWaterTime;
for(int i=0;i<bucket.length;i++){
int bucketSize=vat[i]/pourWaterTime;
if(vat[i]%pourWaterTime!=0){
bucketSize+=1;
}
if(bucketSize>bucket[i])
res+=(bucketSize-bucket[i]);
}
return res;
}
}
总结:
以为整体最优会在局部最优中产生,报错后百思不得其解,看答案后发现无规律。
官方题解给出了两种解法。第一种是贪心加数学,贪心具体做法为将升级水桶操作放于蓄水之前,数学指通过数学简化计算过程。第二种是贪心加优先队列,贪心还是指将升级水桶操作放于蓄水之前,优先队列是指将数据存入大根堆,将需要蓄水操作最大值的数据取出,升级水桶,再将其放入堆,重复此操作直至总操作数不再变小。