38 lines
1.6 KiB
Python
38 lines
1.6 KiB
Python
# Two Sum
|
|
|
|
class Solution:
|
|
def twoSum(self, nums: list[int], target: int) -> list[int]:
|
|
sorted_nums = sorted([(v, i) for i, v in enumerate(nums)], key=lambda x: (x[0], x[1]))
|
|
l, r = 0, len(nums)-1
|
|
while l < r:
|
|
now = sorted_nums[l][0]+sorted_nums[r][0]
|
|
if now < target:
|
|
l += 1
|
|
elif now > target:
|
|
r -= 1
|
|
else:
|
|
return [sorted_nums[l][1], sorted_nums[r][1]]
|
|
|
|
# dict를 활용한 O(n) 풀이
|
|
class Solution:
|
|
def twoSum(self, nums: list[int], target: int) -> list[int]:
|
|
nums_dict = {}
|
|
for i, num in enumerate(nums):
|
|
need_num = target - num
|
|
if need_num in nums_dict:
|
|
return [i, nums_dict[need_num]]
|
|
|
|
nums_dict[num] = i
|
|
|
|
"""
|
|
걸린 시간: 20분
|
|
|
|
복잡도: 정렬할때 O(nlogn)이고, 그 후는 투 포인터로 양 끝에서 오기 때문에 O(n)이다. 따라서 전체 시간복잡도는 O(nlogn)이다.
|
|
정렬한 리스트를 따로 만들기 때문에 공간복잡도는 O(n)이다.
|
|
|
|
해설: 모든 경우의 수를 보면 O(n^2)이기 때문에 다른 방법을 생각했다.
|
|
target을 만드는 두 수를 선택하는 방법을 더해서 크면 하나의 수를 작게 하고, 반대는 크게하는 방식으로 정렬 상태에서 양끝 투포인터를 활용하면 된다는 것을 생각했다.
|
|
|
|
시간복잡도를 O(n)으로 할 수 있는 방법이 있는데, 나오는 숫자들을 dict에 값과 인덱스를 저장하고 지금 보는 숫자로 target을 만들 수 있는 숫자가
|
|
dict에 있는지 확인한다. 한번 순회만 하면 되기 때문에 O(n)이다.
|
|
""" |