邓心一 6 rokov pred
rodič
commit
6ebb8770ed

+ 81 - 0
hard/212.word-search-ii.go

@@ -0,0 +1,81 @@
+func findWords(board [][]byte, words []string) (ans []string) {
+	trie := &TrieNode{}
+	for i := range words {
+		trie.Insert(words[i])
+	}
+	for y := range board {
+		for x := range board[y] {
+			DFS(board, trie, trie, x, y, &ans, []byte{})
+		}
+	}
+	return
+}
+
+func DFS(board [][]byte, trie, curr *TrieNode, x, y int, ans *[]string, prev []byte) {
+	ch := board[y][x]
+	if ch == '*' { // Visited
+		return
+	}
+	curr = curr.OneStepSearch(ch)
+	if curr == nil {
+		return
+	}
+	path := make([]byte, len(prev))
+	copy(path, prev)
+	path = append(path, ch)
+	if curr.IsKey {
+		*ans = append(*ans, string(path))
+		trie.Delete(path)
+	}
+	board[y][x] = '*' // Mark (x, y) as visited
+	if 0 < x {
+		DFS(board, trie, curr, x-1, y, ans, path)
+	}
+	if 0 < y {
+		DFS(board, trie, curr, x, y-1, ans, path)
+	}
+	if x < len(board[0])-1 {
+		DFS(board, trie, curr, x+1, y, ans, path)
+	}
+	if y < len(board)-1 {
+		DFS(board, trie, curr, x, y+1, ans, path)
+	}
+	board[y][x] = ch
+}
+
+type TrieNode struct {
+	Cnt      int
+	IsKey    bool
+	Children *[26]TrieNode
+}
+
+func (root *TrieNode) Insert(word string) {
+	for i := range word {
+		if root.Children == nil {
+			root.Children = &[26]TrieNode{}
+		}
+		root = &root.Children[int(word[i]-'a')]
+		root.Cnt++
+	}
+	root.IsKey = true
+}
+
+func (root *TrieNode) Delete(word []byte) {
+	for i := range word {
+		root = &root.Children[int(word[i]-'a')]
+		root.Cnt--
+	}
+	root.IsKey = false
+}
+
+func (root *TrieNode) OneStepSearch(ch byte) *TrieNode {
+	if root.Children == nil {
+		return nil
+	}
+	root = &root.Children[int(ch-'a')]
+	if root.Cnt == 0 {
+		return nil
+	}
+	return root
+}
+

+ 33 - 0
hard/214.shortest-palindrome.go

@@ -0,0 +1,33 @@
+import (
+	"strings"
+)
+
+func shortestPalindrome(s string) string {
+	l := len(s)
+	if l <= 1 {
+		return s
+	}
+	var i, j int
+	for i = l; i <= 2*l; i++ { // i means the length of the shortest palindrome
+		if i%2 == 1 { // Odd
+			for j = 1; 0 <= l-1-i/2-j && s[l-1-i/2-j] == s[l-1-i/2+j]; j++ {
+			}
+			if l-1-i/2-j < 0 {
+				break
+			}
+		} else { // Even
+			for j = 1; 0 <= l-i/2-j && s[l-i/2-j] == s[l-1-i/2+j]; j++ {
+			}
+			if l-i/2-j < 0 {
+				break
+			}
+		}
+	}
+	idx := l - 1 - i/2 + j
+	var ans strings.Builder
+	for i := l-1; idx <= i; i-- {
+		ans.WriteByte(s[i])
+	}
+	ans.WriteString(s)
+	return ans.String()
+}

+ 3 - 0
hard/218.the-skyline-problem.go

@@ -0,0 +1,3 @@
+func getSkyline(buildings [][]int) [][]int {
+	
+}

+ 25 - 0
medium/230.kth-smallest-element-in-a-bst.go

@@ -0,0 +1,25 @@
+/**
+ * Definition for a binary tree node.
+ * type TreeNode struct {
+ *     Val int
+ *     Left *TreeNode
+ *     Right *TreeNode
+ * }
+ */
+func kthSmallest(root *TreeNode, k int) (val int) {
+	traversalKth(root, &k, &val)
+	return
+}
+
+func traversalKth(node *TreeNode, k *int, val *int) {
+	if node == nil {
+		return
+	}
+	traversalKth(node.Left, k, val)
+	(*k)--
+	if *k == 0 {
+		*val = node.Val
+		return
+	}
+	traversalKth(node.Right, k, val)
+}

+ 27 - 0
medium/236.lowest-common-ancestor-of-a-binary-tree.js

@@ -0,0 +1,27 @@
+/**
+ * Definition for a binary tree node.
+ * function TreeNode(val) {
+ *     this.val = val;
+ *     this.left = this.right = null;
+ * }
+ */
+/**
+ * @param {TreeNode} root
+ * @param {TreeNode} p
+ * @param {TreeNode} q
+ * @return {TreeNode}
+ */
+var lowestCommonAncestor = function(root, p, q) {
+	let la = null
+	const traversal = function(root, p, q) {
+		let set1 = [], set2 = []
+		if (root.left !== null) set1 = traversal(root.left, p, q)
+		if (root.right !== null) set2 = traversal(root.right, p, q)
+		let set3 = new Set([...set1, ...set2])
+		if (root === p || root === q) set3.add(root)
+		if (set3.has(p) && set3.has(q)) { la = root; return [] }
+		return set3
+	}
+	traversal(root, p, q)
+	return la
+}

+ 48 - 0
medium/238.product-of-array-except-self.go

@@ -0,0 +1,48 @@
+func productExceptSelfLong(nums []int) []int {
+	l := len(nums)
+	ans := make([]int, l)
+	zero := false
+	zeroIdx, product := -1, 1
+	for i := 0; i < l; i++ {
+		if nums[i] != 0 {
+			product *= nums[i]
+		} else {
+			if zero {
+				return ans
+			}
+			zero = true
+			zeroIdx = i
+		}
+	}
+	if zero {
+		ans[zeroIdx] = product
+		return ans
+	}
+	for i := 0; i < l; i++ {
+		ans[i] = product / nums[i]
+	}
+	return ans
+}
+
+func productExceptSelf(nums []int) []int {
+	l := len(nums)
+	ans := make([]int, l)
+	memset(ans, 1)
+	for i := 1; i < l; i++ {
+		ans[i] = ans[i-1] * nums[i-1]
+	}
+	for i, tmp := l-2, 1; 0 <= i; i-- {
+		tmp *= nums[i+1]
+		ans[i] *= tmp
+	}
+	return ans
+}
+
+func memset(a []int, v int) {
+	a[0] = v
+	l := len(a)
+	for bp := 1; bp < l; bp *= 2 {
+		copy(a[bp:], a[:bp])
+	}
+}
+

+ 51 - 0
medium/240.search-a-2d-matrix-ii.go

@@ -0,0 +1,51 @@
+func searchMatrix(matrix [][]int, target int) bool {
+	yEnd := len(matrix)
+	if yEnd == 0 {
+		return false
+	}
+	xEnd := len(matrix[0])
+	return searchPartOf(matrix, 0, xEnd, 0, yEnd, target)
+}
+
+func searchPartOf(matrix [][]int, xBeg, xEnd, yBeg, yEnd, target int) bool {
+	m, n := yEnd-yBeg, xEnd-xBeg
+	if m == 0 || n == 0 {
+		return false
+	}
+	if m == 1 { // If m is 1 or n is 1, fall back to binary search.
+		beg, end := xBeg, xEnd
+		for beg < end {
+			mid := beg + (end-beg)/2
+			if matrix[yBeg][mid] < target {
+				beg = mid + 1
+			} else if target < matrix[yBeg][mid] {
+				end = mid
+			} else {
+				return true
+			}
+		}
+		return false
+	} else if n == 1 {
+		beg, end := yBeg, yEnd
+		for beg < end {
+			mid := beg + (end-beg)/2
+			if matrix[mid][xBeg] < target {
+				beg = mid + 1
+			} else if target < matrix[mid][xBeg] {
+				end = mid
+			} else {
+				return true
+			}
+		}
+		return false
+	}
+	if target < matrix[yBeg][xBeg] || matrix[yEnd-1][xEnd-1] < target {
+		return false
+	}
+	xMid, yMid := xBeg+(xEnd-xBeg)/2, yBeg+(yEnd-yBeg)/2
+	return searchPartOf(matrix, xBeg, xMid, yBeg, yMid, target) || // Split the whole matrix into 4 parts.
+		searchPartOf(matrix, xMid, xEnd, yBeg, yMid, target) ||
+		searchPartOf(matrix, xBeg, xMid, yMid, yEnd, target) ||
+		searchPartOf(matrix, xMid, xEnd, yMid, yEnd, target)
+}
+

+ 33 - 0
medium/241.different-ways-to-add-parentheses.go

@@ -0,0 +1,33 @@
+import (
+	"strconv"
+)
+
+var m map[string][]int = make(map[string][]int)
+
+func diffWaysToCompute(input string) (ans []int) {
+	if _, ok := m[input]; ok {
+		return m[input]
+	}
+	for i := range input { // Divide and conquer, use every operator to split input into 2 smaller sub-problems.
+		if ch := input[i]; ch == '+' || ch == '-' || ch == '*' {
+			for _, l := range diffWaysToCompute(input[:i]) {
+				for _, r := range diffWaysToCompute(input[i+1:]) {
+					if ch == '+' {
+						ans = append(ans, l+r)
+					} else if ch == '-' {
+						ans = append(ans, l-r)
+					} else {
+						ans = append(ans, l*r)
+					}
+				}
+			}
+		}
+	}
+	if len(ans) == 0 { // No operator, just a number
+		n, _ := strconv.Atoi(input)
+		ans = append(ans, n)
+	}
+	m[input] = ans
+	return
+}
+