题目
思路
这是一道经典的贪心问题。可以从体重小的人的方面来考虑,当一艘船承载一个体重较小的人后,最节省的方案就是再载一个体重尽量大的人。因为如果不这样的话,这个体重较大的人在后面可能需要一艘单独的船来承载,最终的答案也会变大,这种思路实际上是以尽量小的代价抵消尽量大的代价。具体实现时先对列表进行排序,之后采用类似双指针的方法,令两个指针分别指向第一个元素和最后一个元素。如果当前两个指针指向的人可以做一艘船,则答案加一,左指针右移,右指针左移。否则说明右指针指向的元素只能单独放到一条船里。依次遍历直到两个指针相遇。需要注意的一点是两指针相遇时,右指针上一步可能是单独分给了一艘船,这种情况相当于左指针当前指向的元素还没有放进去,因此答案还要加一。
代码
class Solution:
def numRescueBoats(self, people: List[int], limit: int) -> int:
people.sort()
l=0
r=len(people)-1
ans=0
summ=0 //辅助变量,用来统计已分配船的元素个数,在最后一步特判时使用
while l<r:
if people[l]+people[r]<=limit:
l+=1
r-=1
ans+=1
summ+=2
else:
r-=1
ans+=1
summ+=1
if summ!=len(people):
ans+=1
return ans