[Leetcode] 34. Find First and Last Position of Element in Sorted Array
2024. 4. 2. 06:42ㆍAlgorithm
Problem:
Given an array of integers nums sorted in non-decreasing order, find the starting and ending position of a given target value.
If target is not found in the array, return [-1, -1].
You must write an algorithm with O(log n) runtime complexity.
Example 1:
Input: nums = [5,7,7,8,8,10], target = 8
Output: [3,4]
Example 2:
Input: nums = [5,7,7,8,8,10], target = 6
Output: [-1,-1]
Example 3:
Input: nums = [], target = 0
Output: [-1,-1]
Constraints:
0 <= nums.length <= 105
-109 <= nums[i] <= 109
nums is a non-decreasing array.
-109 <= target <= 109
위 문제는 주어진 nums list에 중복된 숫자가 있다면, 그 수의 시작점과 끝점을 찾는 문제다. 시간복잡도는 O(log(n))으로 이루어져야 한다.
발상:
이 문제의 시간복잡도가 O(log(n))인 것을 보고, Binary Search를 떠올렸다. Binary Search밖에 아는게 없기 때문이다. 하하
코드 짜기:
코드는 내가 직접 100% 짜지 못했다. 그래서 다른 사람들 Solution을 참고했다. 형식은 이렇다.
기존의 Binary Search를 유지하고, left를 탐색할 건지 right를 탐색할건지 조건만 추가해 주는 거였다. left를 탐색하면 start값이 나오고, right를 탐색하면 end값이 나온다.
코드:
class Solution:
def searchRange(self, nums: List[int], target: int) -> List[int]:
def findBound(nums: List[int],target:int, isleft:bool) -> int:
left,right = 0, len(nums)-1
mid = 0
boundary = -1
while left <= right:
mid = (left + right) // 2
if target < nums[mid]:
right = mid - 1
elif target > nums[mid]:
left = mid + 1
else:
boundary = mid
if isleft:
right = mid - 1
else:
left = mid + 1
return boundary
left = findBound(nums,target,True)
if left == -1:
return [-1,-1]
right = findBound(nums,target,False)
return [left,right]
내가 본 Solution1:
class Solution:
def searchRange(self, nums: List[int], target: int) -> List[int]:
left, right = 0, len(nums) - 1
first, last = -1, -1
while left <= right:
mid = left + (right - left) // 2
if nums[mid] == target:
first = mid
last = mid
while first > 0 and nums[first - 1] == target:
first -= 1
while last < len(nums) - 1 and nums[last + 1] == target:
last += 1
return [first, last]
elif nums[mid] < target:
left = mid + 1
else:
right = mid - 1
return [first, last]
내가 본 Solution2:
class Solution:
def searchRange(self, nums: List[int], target: int) -> List[int]:
def findFirst(nums, target):
left, right = 0, len(nums) - 1
first = -1
while left <= right:
mid = left + (right - left) // 2
if nums[mid] == target:
first = mid
right = mid - 1
elif nums[mid] < target:
left = mid + 1
else:
right = mid - 1
return first
def findLast(nums, target):
left, right = 0, len(nums) - 1
last = -1
while left <= right:
mid = left + (right - left) // 2
if nums[mid] == target:
last = mid
left = mid + 1
elif nums[mid] < target:
left = mid + 1
else:
right = mid - 1
return last
first = findFirst(nums, target)
last = findLast(nums, target)
return [first, last]
'Algorithm' 카테고리의 다른 글
[Leetcode] 74. Search a 2D Matrix (0) | 2024.04.04 |
---|---|
[Leetcode] 69. Sqrt(x) (0) | 2024.04.04 |
[Leetcode] 35. Search Insert Position (0) | 2024.04.03 |
[Leetcode] 33. Search in Rotated Sorted Array (0) | 2024.03.30 |
[Leetcode] 442. Find All Duplicates in an Array (1) | 2024.03.26 |