diff --git a/find-median-from-data-stream/yyyyyyyyyKim.py b/find-median-from-data-stream/yyyyyyyyyKim.py new file mode 100644 index 000000000..2d671c30c --- /dev/null +++ b/find-median-from-data-stream/yyyyyyyyyKim.py @@ -0,0 +1,27 @@ +class MedianFinder: + # Follow up : 두 개의 heap 사용해서 구현 가능(시간복잡도 O(log n), 추가 공부 필요함) + # heap 사용하지 않고 이진 탐색 삽입으로 풀었음 + + def __init__(self): + # 숫자 저장할 리스트 생성 + self.arr = [] + + + def addNum(self, num: int) -> None: + # 숫자 추가하고 정렬하기 + # self.arr.append(num) + # self.arr.sort() -> 시간초과(시간복잡도 O(n log n)) + # 이진탐색삽입(시간복잡도 O(n)) + bisect.insort(self.arr, num) + + def findMedian(self) -> float: + # 길이가 홀수면 가운데 값 리턴 + if len(self.arr)%2 == 1: + return self.arr[len(self.arr)//2] + # 길이가 짝수면 가운데 두 수의 평균 리턴 + return (self.arr[len(self.arr)//2-1] + self.arr[len(self.arr)//2]) / 2 + +# Your MedianFinder object will be instantiated and called as such: +# obj = MedianFinder() +# obj.addNum(num) +# param_2 = obj.findMedian() diff --git a/insert-interval/yyyyyyyyyKim.py b/insert-interval/yyyyyyyyyKim.py new file mode 100644 index 000000000..f4546fe5c --- /dev/null +++ b/insert-interval/yyyyyyyyyKim.py @@ -0,0 +1,25 @@ +class Solution: + def insert(self, intervals: List[List[int]], newInterval: List[int]) -> List[List[int]]: + + # 시간복잡도 O(n log n), 공간복잡도 O(n) + + # newInterval 추가하고 정렬 + intervals.append(newInterval) + intervals.sort() + + answer = [intervals[0]] + + for i in range(1, len(intervals)): + prev = answer[-1] + curr = intervals[i] + + # 병합하기 + # answer의 끝 값보다 현재의 시작값이 더 작으면 겹치는 것 -> 현재의 끝값과 answer의 끝값 중 더 큰 값으로 병합 + if curr[0] <= prev[1]: + prev[1] = max(prev[1], curr[1]) + + # 겹치지 않으면 현재값을 answer에 추가 + else: + answer.append(curr) + + return answer diff --git a/kth-smallest-element-in-a-bst/yyyyyyyyyKim.py b/kth-smallest-element-in-a-bst/yyyyyyyyyKim.py new file mode 100644 index 000000000..15f3e9792 --- /dev/null +++ b/kth-smallest-element-in-a-bst/yyyyyyyyyKim.py @@ -0,0 +1,34 @@ +# Definition for a binary tree node. +# class TreeNode: +# def __init__(self, val=0, left=None, right=None): +# self.val = val +# self.left = left +# self.right = right +class Solution: + def kthSmallest(self, root: Optional[TreeNode], k: int) -> int: + + # DFS + # 시간복잡도 최악 O(n)/ 공간복잡도 O(log n) ~ O(n) (재귀깊이) + self.count = 0 + self.answer = None + + def dfs(node): + if not node: + return + + # 가장 작은 값부터(왼쪽서브트리) 재귀로 탐색 + dfs(node.left) + + self.count += 1 + + # k번째 작은 값 찾으면 바로 종료하기 + if self.count == k: + self.answer = node.val + return + + # 오른쪽 서브트리 탐색 + dfs(node.right) + + dfs(root) + + return self.answer diff --git a/lowest-common-ancestor-of-a-binary-search-tree/yyyyyyyyyKim.py b/lowest-common-ancestor-of-a-binary-search-tree/yyyyyyyyyKim.py new file mode 100644 index 000000000..af91d76d4 --- /dev/null +++ b/lowest-common-ancestor-of-a-binary-search-tree/yyyyyyyyyKim.py @@ -0,0 +1,22 @@ +# Definition for a binary tree node. +# class TreeNode: +# def __init__(self, x): +# self.val = x +# self.left = None +# self.right = None + +class Solution: + def lowestCommonAncestor(self, root: 'TreeNode', p: 'TreeNode', q: 'TreeNode') -> 'TreeNode': + + # BST(이진 탐색 트리) 특성 활용해서 밸류값으로 LCA 찾기 + # 시간복잡도 O(log n)/ 최악O(n), 공간복잡도 O(1) + while root: + # p, q가 둘 다 root보다 작으면, LCA는 왼쪽 서브트리에 있음 + if p.val < root.val and q.val < root.val: + root = root.left + # p, q가 둘 다 root보다 크면, LCA는 오른쪽 서브트리에 있음 + elif p.val > root.val and q.val > root.val: + root = root.right + # p, q가 root의 양쪽에 나눠져 있는 경우 -> root가 LCA + else: + return root diff --git a/meeting-rooms/yyyyyyyyyKim.py b/meeting-rooms/yyyyyyyyyKim.py new file mode 100644 index 000000000..840809a8e --- /dev/null +++ b/meeting-rooms/yyyyyyyyyKim.py @@ -0,0 +1,38 @@ +from typing import ( + List, +) +from lintcode import ( + Interval, +) + +""" +Definition of Interval: +class Interval(object): + def __init__(self, start, end): + self.start = start + self.end = end +""" + +class Solution: + """ + @param intervals: an array of meeting time intervals + @return: if a person could attend all meetings + """ + def can_attend_meetings(self, intervals: List[Interval]) -> bool: + + # 시간복잡도(O(n^2)), 공간복잡도 O(1) + # 시작점을 기준으로 정렬(선택정렬) + for i in range(len(intervals)): + idx = i + for j in range(i+1,len(intervals)): + if intervals[j].start < intervals[idx].start: + idx = j + if idx != i: + intervals[i], intervals[idx] = intervals[idx], intervals[i] + + # 겹치는 회의 있는지 확인 + for i in range(1, len(intervals)): + if intervals[i].start < intervals[i-1].end: + return False + + return True