Problem Description
You are given an array people where people[i] is the weight of the ith person, and an infinite number of boats where each boat can carry a maximum weight of limit. Each boat carries at most two people at the same time, provided the sum of the weight of those people is at most limit.
Return the minimum number of boats to carry every given person.
Examples
Example 1:
Input: people = [1,2], limit = 3 Output: 1 Explanation: 1 boat (1, 2) Example 2:
Input: people = [3,2,2,1], limit = 3 Output: 3 Explanation: 3 boats (1, 2), (2) and (3) Example 3:
Input: people = [3,5,3,4], limit = 5 Output: 4 Explanation: 4 boats (3), (3), (4), (5)
Thought Process / Intuition
Maximum no. of boats = len(people), one person one boat. First approach: Sort people, binary search from 0 to Maximum no. of boats, check if is_valid for that no. of boats, problem is is_valid function how to check in efficient run time? Second approach: Greedy solution. The greedy choice is to try and pair the heaviest remaining person with the lighest remaining person. If the sum of their weights is less than or equal to the limit, we can pair them together. Otherwise, we can pair the heaviest person with themselves. This is because the heaviest person cannot be paired with anyone else, so they must be in their own boat. We can implement this greedy choice by sorting the list of people in ascending order and using two pointers to iterate through the list from the start and end. We pair the people at the pointers together if their sum is less than or equal to the limit, and we increment the pointer at the start. We decrement the pointer at the end in each iteration. We continue this process until the pointers meet, and we return the minimum number of boats used.
Approach
- Sort the list
people
in ascending order. - Initialize two pointers
left
andright
to the start and end of the list, respectively. - Initialize a variable
boats_used
to store the minimum number of boats required. - Iterate through the list
people
until the pointersleft
andright
meet. - If the sum of the weights of the people at the pointers
left
andright
is less than or equal to the limit, increment the pointerleft
. - Decrement the pointer
right
in each iteration. - Increment the variable
boats_used
by 1 in each iteration. - Return the minimum number of boats required.
Solution
class Solution:
def numRescueBoats(self, people: List[int], limit: int) -> int:
people.sort()
left , right = 0, len(people) - 1
boats_used = 0
while left <= right:
if people[left] + people[right] <= limit:
left += 1
right -= 1
boats_used += 1
return boats_used
Complexity Analysis
Time complexity:
- The time complexity of the solution is , where is the length of the input list
people
. - We sort the list
people
in time. - We iterate through the list
people
once to find the minimum number of boats required. - The overall time complexity is .
Space complexity:
- The space complexity of the solution is .
- We use a constant amount of extra space to store the variables
left
,right
, andboats_used
. - The space complexity is independent of the input size.