1482. 制作 m 束花所需的最少天数 #
- 标签:数组、二分查找
- 难度:中等
题目大意 #
给定一个整数数组 bloomDay
,以及两个整数 m
和 k
。bloomDay
代表花朵盛开的时间,bloomDay[i]
表示第 i
朵花的盛开时间。盛开后就可以用于一束花中。
现在需要制作 m
束花。制作花束时,需要使用花园中相邻的 k
朵花 。
要求:返回从花园中摘 m
束花需要等待的最少的天数。如果不能摘到 m
束花则返回 -1
。
解题思路 #
这道题跟「 0875. 爱吃香蕉的珂珂」、「 1011. 在 D 天内送达包裹的能力」有点相似。
根据题目可知:
- 制作花束最少使用时间跟花朵开花最短时间有关系,即
min(bloomDay)
。 - 制作花束最多使用时间跟花朵开花最长时间有关系,即
max(bloomDay)
。 - 则制作花束所需要的天数就变成了一个区间
[min(bloomDay), max(bloomDay)]
。
那么,我们就可以根据这个区间,利用二分查找算法找到一个符合题意的最少天数。而判断某个天数下能否摘到 m
束花则可以写个方法判断。具体步骤如下:
- 遍历数组
bloomDay
。 - 如果
bloomDay[i]
小于等于天数days
。就将花朵数量 + 1。- 当能摘的花朵数等于
k
时,能摘的花束数目 + 1,花朵数量置为0
。
- 当能摘的花朵数等于
- 如果
bloomDay[i]
大于天数days
。就将花朵数置为0
。 - 最后判断能摘的花束数目是否大于等于
m
。
整个算法的步骤如下:
- 如果
m * k
大于len(bloomDay)
,说明无法满足要求,直接返回-1
。 - 使用两个指针
left
、right
。令left
指向min(bloomDay)
,right
指向max(bloomDay)
。代表待查找区间为[left, right]
。 - 取两个节点中心位置
mid
,判断是否能在mid
天制作m
束花。- 如果不能,则将区间
[left, mid]
排除掉,继续在区间[mid + 1, right]
中查找。 - 如果能,说明天数还可以继续减少,则继续在区间
[left, mid]
中查找。
- 如果不能,则将区间
- 当
left == right
时跳出循环,返回left
。
代码 #
|
|