diff --git a/combination-sum/dev-jonghoonpark.md b/combination-sum/dev-jonghoonpark.md new file mode 100644 index 000000000..8e6a352e8 --- /dev/null +++ b/combination-sum/dev-jonghoonpark.md @@ -0,0 +1,78 @@ +- https://leetcode.com/problems/combination-sum/ +- time complexity : O(2^n) +- space complexity : O(2^n) +- https://algorithm.jonghoonpark.com/2024/06/23/leetcode-39 + +## bfs 로 풀기 + +```java +class Solution { + public List> combinationSum(int[] candidates, int target) { + Arrays.sort(candidates); + List> result = new ArrayList<>(); + + Queue queue = new LinkedList<>(); + queue.offer(new Holder(target)); + + while (!queue.isEmpty()) { + Holder holder = queue.poll(); + int lastInput = !holder.combination.isEmpty() ? holder.combination.get(holder.combination.size() - 1) : 0; + int left = holder.left; + if (left == 0) { + result.add(holder.combination); + continue; + } + + for (int candidate : candidates) { + if (candidate < lastInput) { + continue; + } + + if (left - candidate >= 0) { + queue.add(holder.next(candidate)); + } else { + break; + } + } + } + + return result; + } +} + +class Holder { + int left; + List combination; + + public Holder(int left) { + this.left = left; + this.combination = new ArrayList<>(); + } + + private Holder(int left, List combination) { + this.left = left; + this.combination = combination; + } + + public Holder next(int minus) { + List combinedList = new ArrayList<>(this.combination.size() + 1); + combinedList.addAll(this.combination); + combinedList.add(minus); + return new Holder(this.left - minus, combinedList); + } + + @Override + public String toString() { + return "{" + + "left=" + left + + ", combination=" + combination + + '}'; + } +} +``` + +## backtracking 으로 풀기 + +```java +// TODO +``` diff --git a/construct-binary-tree-from-preorder-and-inorder-traversal/dev-jonghoonpark.md b/construct-binary-tree-from-preorder-and-inorder-traversal/dev-jonghoonpark.md new file mode 100644 index 000000000..63a958331 --- /dev/null +++ b/construct-binary-tree-from-preorder-and-inorder-traversal/dev-jonghoonpark.md @@ -0,0 +1,110 @@ +- https://leetcode.com/problems/construct-binary-tree-from-preorder-and-inorder-traversal/ +- time complexity : O(n) +- space complexity : O(n) +- https://algorithm.jonghoonpark.com/2024/06/23/leetcode-105 + +```java +class Solution { + public TreeNode buildTree(int[] preorder, int[] inorder) { + Map inorderIndexMap = new HashMap<>(); + for (int i = 0; i < inorder.length; i++) { + inorderIndexMap.put(inorder[i], i); + } + + return buildTree(inorderIndexMap, new Traversal(preorder), new Traversal(inorder)); + } + + public TreeNode buildTree(Map inorderIndexMap, Traversal preorderTraversal, Traversal inorderTraversal) { + if(preorderTraversal.start > preorderTraversal.end) { + return null; + } + + TreeNode treeNode = new TreeNode(preorderTraversal.getFirst()); + if(preorderTraversal.start == preorderTraversal.end) { + return treeNode; + } + + int rootIndex = inorderIndexMap.get(preorderTraversal.getFirst()); + int leftSize = rootIndex - inorderTraversal.start; + treeNode.left = buildTree( + inorderIndexMap, + preorderTraversal.subIterator(preorderTraversal.start + 1, preorderTraversal.start + leftSize), + inorderTraversal.subIterator(inorderTraversal.start, rootIndex - 1) + ); + treeNode.right = buildTree( + inorderIndexMap, + preorderTraversal.subIterator(preorderTraversal.start + leftSize + 1, preorderTraversal.end), + inorderTraversal.subIterator(rootIndex + 1, inorderTraversal.end) + ); + + return treeNode; + } +} + +class TreeNode { + int val; + TreeNode left; + TreeNode right; + + TreeNode() { + } + + TreeNode(int val) { + this.val = val; + } + + TreeNode(int val, TreeNode left, TreeNode right) { + this.val = val; + this.left = left; + this.right = right; + } + + @Override + public String toString() { + return "{" + + "val=" + val + + ", left=" + left + + ", right=" + right + + '}'; + } +} + +class Traversal { + int[] array; + int start; + int end; + + public Traversal(int[] array) { + this.array = array; + this.start = 0; + this.end = array.length - 1; + } + + private Traversal(int[] array, int start, int end) { + this.array = array; + this.start = start; + this.end = end; + } + + public Traversal subIterator(int start, int end) { + return new Traversal(array, start, end); + } + + public int getFirst() { + return array[start]; + } + + public Traversal(int start, int end) { + this.start = start; + this.end = end; + } + + @Override + public String toString() { + return "{" + + "start=" + start + + ", end=" + end + + '}'; + } +} +``` diff --git a/implement-trie-prefix-tree/dev-jonghoonpark.md b/implement-trie-prefix-tree/dev-jonghoonpark.md new file mode 100644 index 000000000..f39e153f0 --- /dev/null +++ b/implement-trie-prefix-tree/dev-jonghoonpark.md @@ -0,0 +1,58 @@ +- https://leetcode.com/problems/implement-trie-prefix-tree/ +- https://algorithm.jonghoonpark.com/2024/06/23/leetcode-208 + +## TC, SC + +insert, search, startsWith 메소드의 경우 입력된 문자열의 길이를 n 이라 하였을 때 시간 복잡도는 `O(n)`이다. 공간 복잡도는 `insert된 문자열의 갯수` 를 `N` 이라 하고 `insert된 문자열의 길이의 평균` 를 `L`이라고 하였을 때 `O(N * L * 26)`이다. 26은 계수이기 때문에 생략할 수 있다. + +## 풀이 + +```java +class Trie { + + Node root = new Node(); + + public Trie() { + + } + + public void insert(String word) { + Node currentNode = root; + for(char c : word.toCharArray()) { + if(currentNode.nodes[c - 97] == null) { + currentNode.nodes[c - 97] = new Node(); + } + currentNode = currentNode.nodes[c - 97]; + } + currentNode.val = word; + } + + public boolean search(String word) { + Node currentNode = root; + for(char c : word.toCharArray()) { + if(currentNode.nodes[c - 97] == null) { + return false; + } + currentNode = currentNode.nodes[c - 97]; + } + + return currentNode.val != null && currentNode.val.equals(word); + } + + public boolean startsWith(String prefix) { + Node currentNode = root; + for(char c : prefix.toCharArray()) { + if(currentNode.nodes[c - 97] == null) { + return false; + } + currentNode = currentNode.nodes[c - 97]; + } + return true; + } +} + +class Node { + String val; + Node[] nodes = new Node[26]; +} +``` diff --git a/kth-smallest-element-in-a-bst/dev-jonghoonpark.md b/kth-smallest-element-in-a-bst/dev-jonghoonpark.md new file mode 100644 index 000000000..066555301 --- /dev/null +++ b/kth-smallest-element-in-a-bst/dev-jonghoonpark.md @@ -0,0 +1,44 @@ +- https://leetcode.com/problems/kth-smallest-element-in-a-bst/ +- time complexity : O(n) +- space complexity : O(n), 트리가 균등할 경우 O(logn)에 가까워진다. +- https://algorithm.jonghoonpark.com/2024/06/23/leetcode-230 + +```java +class Solution { + public int kthSmallest(TreeNode root, int k) { + return dfs(root, new Holder(k)); + } + + public int dfs(TreeNode root, Holder holder) { + if(root.left != null) { + int left = dfs(root.left, holder); + if (left != -1) { + return left; + } + } + holder.decrease(); + if (holder.k == 0) { + return root.val; + } + if(root.right != null) { + int right = dfs(root.right, holder); + if (right != -1) { + return right; + } + } + return -1; + } +} + +class Holder { + int k; + + public Holder(int k) { + this.k = k; + } + + public void decrease() { + this.k = this.k - 1; + } +} +``` diff --git a/word-search/dev-jonghoonpark.md b/word-search/dev-jonghoonpark.md new file mode 100644 index 000000000..aa147d139 --- /dev/null +++ b/word-search/dev-jonghoonpark.md @@ -0,0 +1,48 @@ +- https://leetcode.com/problems/word-search/ +- https://algorithm.jonghoonpark.com/2024/06/23/leetcode-79 + +## TC, SC + +`board` 의 길이를 `w`, `board[i]`의 길이를 `h`, 단어의 길이를 `n` 이라고 하였을 때. +시간 복잡도는 `O(w * h * n)` 이다. 공간 복잡도는 `O(n)`이다. + +## 풀이 + +```java +class Solution { + public boolean exist(char[][] board, String word) { + char[] chars = word.toCharArray(); + for (int i = 0; i < board.length; i++) { + for (int j = 0; j < board[0].length; j++) { + if (dfs(board, chars, i, j, 0, word.length() - 1)) { + return true; + } + } + } + + return false; + } + + public boolean dfs(char[][] board, char[] chars, int i, int j, int pointer, int end) { + if (i < 0 || i > board.length - 1 || j < 0 || j > board[0].length - 1 || board[i][j] != chars[pointer]) { + return false; + } + + if(pointer == end) { + return true; + } + + int next = pointer + 1; + char temp = board[i][j]; + board[i][j] = ' '; + boolean result = dfs(board, chars, i + 1, j, next, end) + || dfs(board, chars, i - 1, j, next, end) + || dfs(board, chars, i, j + 1, next, end) + || dfs(board, chars, i, j - 1, next, end); + if(!result) { + board[i][j] = temp; + } + return result; + } +} +```