Week 2-1. [Hash Table] 219. Contains Duplicate II (Python3)
๋ฌธ์ ํด๊ฒฐ ๊ณผ์
โ๏ธ ๋๋ง์ ๋ฐฉ์์ผ๋ก ๋ฌธ์ ์ ๋ฆฌํ๊ธฐ (=์ฒด๊ณํ)
Contains Duplicate II - LeetCode
Can you solve this real interview question? Contains Duplicate II - Given an integer array nums and an integer k, return true if there are two distinct indices i and j in the array such that nums[i] == nums[j] and abs(i - j) <= k. Example 1: Input: nums
leetcode.com
์ฃผ์ด์ง ๋ฆฌ์คํธ ๋ด์ ๋ ๊ฐ์ ์๋ก ๋ค๋ฅธ ์ธ๋ฑ์ค i์ j๊ฐ ์กด์ฌํ์ฌ nums[i]==nums[j]๋ฅผ ๋ง์กฑํ๋ฉด์ abs(i-j) <= k ๋ผ๋ฉด, True๋ฅผ ๋ฐํํ๋ผ.
- | nums | ∈ [1, 10^4]
๐ ์ด๋ค ์์ผ๋ก ์ ๊ทผํ๋๊ฐ?
defaultdict๋ฅผ ์ฌ์ฉํ์ฌ nums์ ๊ฐ์ key๋ก, ์ธ๋ฑ์ค๋ฅผ value๋ก ์ ์ฅํ๋ค.
์ด ๋ ๊ฐ์ ๊ฐ์ ๊ฐ์ง ์์๋ค์ ์ธ๋ฑ์ค๋ ๋ฆฌ์คํธ ์์ ๋์ ๋๋ค.
์ด์ ๋์ ๋๋ฆฌ์ values๋ฅผ ์ํํ๋ฉด์ ์ ๋๊ฐ์ด k ์ดํ์ธ i์ j๊ฐ ์๋ค๋ฉด True๋ฅผ ๋ฐํํ๊ณ ์ข ๋ฃํ๋ค.
๐ ์๊ณ ๋ฆฌ์ฆ ์ ํ: ์ ๋ ฅ์ ํฌ๊ธฐ๋ฅผ ๋ฐํ์ผ๋ก
๋์ ๋๋ฆฌ๋ฅผ ์ด์ฉํ์ฌ ๊ฐ์ ๊ฐ์ ๊ฐ์ง ์์๋ค์ ์ธ๋ฑ์ค๋ค์ ์ด๊ธฐํํ๋ค.
๐ ์์ฌ ์ฝ๋
dic = defaultdict(list)
enumerate(nums)๋ฅผ ์ํํ๋ฉฐ:
dic[x]์ i๋ฅผ ์ถ๊ฐํ๋ค.
dic.values()๋ฅผ ์ํํ๋ฉฐ:
๊ธธ์ด๊ฐ 1๋ณด๋ค ํฌ๋ฉด์ ๊ฑฐ๋ฆฌ๊ฐ k๋ณด๋ค ์์ผ๋ฉด:
return True
return False
๐ฏ ๊ตฌํ ์ฝ๋
from collections import defaultdict
class Solution:
def containsNearbyDuplicate(self, nums: List[int], k: int) -> bool:
dic = defaultdict(list)
for i, x in enumerate(nums):
dic[x].append(i)
for v in dic.values():
if len(v) <= 1: continue # nums[i] == nums[j]์ธ i, j๊ฐ ์กด์ฌํ์ง ์๋ ๊ฒฝ์ฐ
for i in range(len(v)-1):
if abs(v[i] - v[i+1]) <= k: return True
return False
๋ง์ฝ nums๊ฐ [1, 0, 1, 1]์ด๋ผ๋ฉด, ๋์ ๋๋ฆฌ๋ ์๋์ ๊ฐ์ด ์ด๊ธฐํ ๋๋ค.
{
1: [0, 2, 3],
0: [1]
}
๋ด ์ฝ๋๋ฅผ ํ๊ตฌํด๋ณด๊ธฐ
โฑ ์ฑ๋ฅ ์ธก์ (์๊ฐ๋ณต์ก๋/๊ณต๊ฐ๋ณต์ก๋)
linear search๋ก ์๊ฐ๋ณต์ก๋๋ O(n)์ด๋ค.
โ๏ธ ์ฑ๋ฅ ํ๊ณ
1์ด์ ์๊ฐ ์ ํ์ ๊ฐ๋๋ค๊ณ ํ ๋, O(n)์ ์๊ฐ ๋ณต์ก๋๋ฅผ ๊ฐ์ง ์ฝ๋์์ ์ ๋ ฅ์ ์ต๋ ํฌ๊ธฐ n์ ๋๋ต 10^6์ด๋ค.
๋ฌธ์ ์์ ์ ๋ ฅ์ ์ต๋ ํฌ๊ธฐ๋ 10^5์ด๋ฏ๋ก ์์ ์ ์ผ๋ก ์ฒ๋ฆฌํ ์ ์๋ค.
๐ก ๋ฌด์์/์ด๋ป๊ฒ ๊ฐ์ ํ ์ ์์๊น?
dic.values()๋ฅผ ์ํํ๋ฉฐ ๊ฑฐ๋ฆฌ(์ ๋๊ฐ)๊ฐ k ์ดํ์ธ ๋ ์์๋ฅผ ์ฒดํฌํ ๋์ ๋ก์ง์ ๊ฐ์ ํ๊ณ ์ถ๋ค.
abs(v[i]-v[i+1])๋ก ๋ชจ๋ v๋ฅผ ์ฒดํฌํ์ง ์๊ณ ํ๋ฒ์ ๊ตฌํ ์๋ ์์๊น?
๋ค๋ฅธ ์ฌ๋์ ์ฝ๋๋ฅผ ํ๊ตฌํด๋ณด๊ธฐ
๐ฏ ๊ตฌํ ์ฝ๋
set ์๋ฃ๊ตฌ์กฐ๋ฅผ ํ์ฉํ ํ์ด๋ก, set ์์ ํญ์ k๊ฐ์ ์์๋ฅผ ์ ์งํ๋ค.
nums๋ฅผ ์ํํ๋ฉด์, ํน์ ์์(nums[i])๊ฐ set ์์ ์กด์ฌํ๋ค๋ ๊ฒ์ ํด๋น ์์(nums[i])์ set ์์ ์๋ ์์๋ค๊ณผ์ ๊ฑฐ๋ฆฌ๊ฐ k ์ดํ๋ผ๋ ์๋ฏธ์ด๋ค.
๋ง์ฝ set์ ๊ธธ์ด๊ฐ k+1์ด ๋๋ค๋ฉด, set ์์์ nums[i-k] ์์๋ฅผ ์ ๊ฑฐํ๋ค.
(nums[i-k]๋ ๊ฐ์ฅ ์ต๊ทผ์ ๋ค์ด์จ ์์(nums[i])๋ก๋ถํฐ ๊ฑฐ๋ฆฌ๊ฐ k์ธ ์์๋ก ๊ฐ์ฅ ์ฒ์ ๋ค์ด์จ ์์๋ฅผ ์๋ฏธํ๋ค.)
class Solution:
def containsNearbyDuplicate(self, nums: List[int], k: int) -> bool:
if k == 0: return False
st = set()
for i in range(len(nums)):
if nums[i] in st: return True
st.add(nums[i])
if len(st) == k+1:
st.remove(nums[i-k])
return False
โฑ ์ฑ๋ฅ ์ธก์ (์๊ฐ๋ณต์ก๋/๊ณต๊ฐ๋ณต์ก๋)
linear search๋ก O(n)์ ์๊ฐ๋ณต์ก๋๋ฅผ ๊ฐ์ง๋ค.
๋๋ ์
set ์๋ฃ๊ตฌ์กฐ๋ฅผ ํ์ฉํ์ฌ set ์์ k๊ฐ์ ์์๋ฅผ ์ ์งํ๋ ๋ฐฉ๋ฒ์ ์ ๋ง ์๊ฐ์น ๋ชปํ๋ค.
"set์ ์์๋ฅผ ๋ณด์ฅํ์ง ์๋๋ฐ, set ๋์ ๋ฆฌ์คํธ๋ฅผ ์จ์ผํ๋ ๊ฒ์ด ์๋๊ฐ?" ์ถ์์ง๋ง, set ๋ด๋ถ์์ ๊ฐ์ด nums[i-k]์ธ ์์๋ฅผ ์ ๊ฑฐํ๋ฉด ๋๋ฏ๋ก ์์๋ฅผ ๋ณด์ฅํ ํ์๊ฐ ์๋ค.
๋ฐ๋ผ์ ์ค๋ณต์ ์ ๊ฑฐํด์ฃผ๋ set์ ์ฌ์ฉํ๋๊ฒ ํจ์จ์ ์ด๋ค.