You are given an array points
, an integer angle
, and your location
, where location = [posx, posy]
and points[i] = [xi, yi]
both denote integral coordinates on the X-Y plane.
Initially, you are facing directly east from your position. You cannot move from your position, but you can rotate. In other words, posx
and posy
cannot be changed. Your field of view in degrees is represented by angle
, determining how wide you can see from any given view direction. Let d
be the amount in degrees that you rotate counterclockwise. Then, your field of view is the inclusive range of angles [d - angle/2, d + angle/2]
.
You can see some set of points if, for each point, the angle formed by the point, your position, and the immediate east direction from your position is in your field of view.
There can be multiple points at one coordinate. There may be points at your location, and you can always see these points regardless of your rotation. Points do not obstruct your vision to other points.
Return the maximum number of points you can see.
Example 1:
Input: points = [[2,1],[2,2],[3,3]], angle = 90, location = [1,1] Output: 3 Explanation: The shaded region represents your field of view. All points can be made visible in your field of view, including [3,3] even though [2,2] is in front and in the same line of sight.
Example 2:
Input: points = [[2,1],[2,2],[3,4],[1,1]], angle = 90, location = [1,1] Output: 4 Explanation: All points can be made visible in your field of view, including the one at your location.
Example 3:
Input: points = [[1,0],[2,1]], angle = 13, location = [1,1] Output: 1 Explanation: You can only see one of the two points, as shown above.
Constraints:
1 <= points.length <= 105
points[i].length == 2
location.length == 2
0 <= angle < 360
0 <= posx, posy, xi, yi <= 100
When you get asked this question in a real-life environment, it will often be ambiguous (especially at FAANG). Make sure to ask these questions in that case:
The brute force approach to finding the maximum visible points is all about trying out every possible combination of points and checking which one gives us the best view. It’s like manually looking at every possibility to find the best one, even if it takes a long time. We are trying out all the possible angles and see which one contains the most points.
Here's how the algorithm would work step-by-step:
import math
def maximum_number_of_visible_points_brute_force(points, angle_degrees, location):
maximum_visible_points = 0
same_location_points_count = 0
for point in points:
if point[0] == location[0] and point[1] == location[1]:
same_location_points_count += 1
for first_point_index in range(len(points)):
for second_point_index in range(first_point_index + 1, len(points)):
# Consider every pair of points as the angle boundaries.
angle1 = math.atan2(points[first_point_index][1] - location[1], points[first_point_index][0] - location[0]) * 180 / math.pi
angle2 = math.atan2(points[second_point_index][1] - location[1], points[second_point_index][0] - location[0]) * 180 / math.pi
viewing_angle = abs(angle1 - angle2)
viewing_angle = min(viewing_angle, 360 - viewing_angle)
if viewing_angle > angle_degrees:
continue
visible_points_count = 0
# Count points within the calculated viewing angle
for third_point_index in range(len(points)):
if third_point_index == first_point_index or third_point_index == second_point_index:
continue
angle3 = math.atan2(points[third_point_index][1] - location[1], points[third_point_index][0] - location[0]) * 180 / math.pi
viewing_angle_with_first = abs(angle1 - angle3)
viewing_angle_with_first = min(viewing_angle_with_first, 360 - viewing_angle_with_first)
viewing_angle_with_second = abs(angle2 - angle3)
viewing_angle_with_second = min(viewing_angle_with_second, 360 - viewing_angle_with_second)
# Check if the third point is inside the viewing angle
if viewing_angle_with_first + viewing_angle_with_second <= viewing_angle + 1e-6:
visible_points_count += 1
maximum_visible_points = max(maximum_visible_points, visible_points_count + 2)
return maximum_visible_points + same_location_points_count
The key is to sort points by their angle relative to your location. Then, we use a sliding window approach to find the maximum number of points within your field of view, handling cases where points wrap around (like going past 360 degrees).
Here's how the algorithm would work step-by-step:
import math
def maximum_number_of_visible_points(points, angle, location):
same_location_points = 0
angles = []
for point in points:
x_difference = point[0] - location[0]
y_difference = point[1] - location[1]
if x_difference == 0 and y_difference == 0:
same_location_points += 1
else:
angle_degrees = math.atan2(y_difference, x_difference) * 180 / math.pi
angles.append(angle_degrees if angle_degrees >= 0 else angle_degrees + 360)
angles.sort()
# Handle circular nature by duplicating angles
extended_angles = angles + [ang + 360 for ang in angles]
max_points = 0
window_start = 0
window_end = 0
while window_end < len(extended_angles):
# Expand window until angle exceeds field of view
while window_end < len(extended_angles) and \
extended_angles[window_end] - extended_angles[window_start] <= angle:
window_end += 1
# Update the maximum number of points
max_points = max(max_points, window_end - window_start)
# Shrink window from the left
window_start += 1
# Points at the same location are always visible
return max_points + same_location_points
Case | How to Handle |
---|---|
Empty points array | Return 0, as no points can be visible. |
All points are at the same location as the location | Count these points separately as they are always visible. |
Extremely large input (number of points close to the maximum allowed) | Ensure the solution scales efficiently, potentially using optimized sorting or data structures. |
Extremely small angular difference between points | Floating-point precision issues may arise; use an epsilon value for comparisons. |
View angle is 0 or 360 degrees | Handle cases where the view angle doesn't allow for any points to be seen, and return appropriate value, likely 0. |
Points that form angles that are 0, 90, 180 or 270 degrees relative to location (axis aligned points) | Test all quadrants and boundaries accurately for corner test cases. |
Location is extremely far from the points | Calculations might result in zero angles, and we need to handle them correctly and compare them with epsilon value. |
Points with identical angles relative to location | Count all points with identical angles within view angle. |