Bläddra i källkod

finished no.4, no.90

dengxinyi 6 år sedan
förälder
incheckning
d7833bf18d
4 ändrade filer med 82 tillägg och 73 borttagningar
  1. 57 13
      hard/4.go
  2. 2 2
      medium/11.go
  3. 19 56
      medium/90.go
  4. 4 2
      medium/91.go

+ 57 - 13
hard/4.go

@@ -1,23 +1,67 @@
 package main
 package main
 
 
-import (
-	"fmt"
-)
+import "fmt"
 
 
-// nums1 & nums2 is not empty
+// len(nums1) + len(nums2) != 0
 func findMedianSortedArrays(nums1 []int, nums2 []int) float64 {
 func findMedianSortedArrays(nums1 []int, nums2 []int) float64 {
-	midIdx1 := len(nums1) / 2
-	var mid1 float64
-	if len(nums1)%2 == 0 {
-		mid1 = float64(nums1[midIdx1-1]+nums1[midIdx1]) / 2
-	} else {
-		mid1 = float64(nums1[midIdx1])
+	// Use i, j to divide A, B into 2 parts, like
+	// [A(0), ... , A(i-1), | A(i), ... , A(m)] and
+	// [B(0), ... , B(j-1), | B(j), ... , B(n)],
+	// then the left part of A and B is left, the right
+	// part is right, when max(left) <= min(right) &&
+	// len(left) == len(right), we can find the median by
+	// median = [max(left) + min(right)] / 2
+	m, n := len(nums1), len(nums2)
+	// if m < n, i ~ [0, m], j = (m+n+1)/2 - i
+	if m > n { // if m > n, swap nums1, nums2
+		nums1, nums2, m, n = nums2, nums1, n, m
 	}
 	}
-	return mid1
+	ibeg, iend, halfLen := 0, m, (m+n+1)/2
+	var i, j int
+	for ibeg <= iend {
+		i = (ibeg + iend) / 2
+		j = halfLen - i
+		if i > 0 && nums1[i-1] > nums2[j] { // A[i-1]'s too big, ie. i's too big
+			iend = i - 1
+		} else if i < m && nums2[j-1] > nums1[i] { // i's too small
+			ibeg = i + 1
+		} else {
+			// i, j is found (A[i-1] <= B[j] && B[j-1] <= A[i])
+			var maxOfLeft, minOfRight int
+			if i == 0 { // find max of left
+				maxOfLeft = nums2[j-1]
+			} else if j == 0 {
+				maxOfLeft = nums1[i-1]
+			} else {
+				maxOfLeft = nums1[i-1]
+				if nums2[j-1] > maxOfLeft {
+					maxOfLeft = nums2[j-1]
+				}
+			}
+			if (m+n)%2 != 0 { // if odd, return max of left as median (!!!)
+				return float64(maxOfLeft)
+			}
+			if i == m { // find min of right
+				minOfRight = nums2[j]
+			} else if j == n {
+				minOfRight = nums1[i]
+			} else {
+				minOfRight = nums1[i]
+				if nums2[j] < nums1[i] {
+					minOfRight = nums2[j]
+				}
+			}
+			return float64(maxOfLeft+minOfRight) / 2
+		}
+	}
+	return -1 // not found, useless
 }
 }
 
 
 func main() {
 func main() {
-	nums1 := []int{1, 2, 3}
-	nums2 := []int{2, 5, 6}
+	nums1 := []int{1, 3}
+	nums2 := []int{2}
 	fmt.Println(findMedianSortedArrays(nums1, nums2))
 	fmt.Println(findMedianSortedArrays(nums1, nums2))
+	nums3 := []int{}
+	nums4 := []int{1}
+	fmt.Println(findMedianSortedArrays(nums3, nums4))
 }
 }

+ 2 - 2
medium/11.go

@@ -1,11 +1,11 @@
 package main
 package main
 
 
-/* func minInt(x, y int) int {
+func minInt(x, y int) int {
 	if x < y {
 	if x < y {
 		return x
 		return x
 	}
 	}
 	return y
 	return y
-} */
+}
 
 
 // 穷举
 // 穷举
 func maxAreaOld(height []int) int {
 func maxAreaOld(height []int) int {

+ 19 - 56
medium/90.go

@@ -1,67 +1,30 @@
 package main
 package main
 
 
 import (
 import (
-	"fmt"
 	"sort"
 	"sort"
 )
 )
 
 
-func minInt(x, y int) int {
-	if x < y {
-		return x
-	}
-	return y
-}
-
-// Int2DSlice ...
-type Int2DSlice [][]int
-
-func (p Int2DSlice) Len() int { return len(p) }
-func (p Int2DSlice) Less(i, j int) bool {
-	if len(p[i]) == 0 || len(p[j]) == 0 {
-		return len(p[i]) == 0
-	}
-	bound := minInt(len(p[i]), len(p[j]))
-	for k := 0; k < bound; k++ {
-		if p[i][k] != p[j][k] {
-			return p[i][k] < p[j][k]
-		}
-	}
-	return len(p[i]) < len(p[j])
-}
-func (p Int2DSlice) Swap(i, j int) { p[i], p[j] = p[j], p[i] }
-
-func subsetsWithDupIter(nums []int, subsets [][]int, subsetsMap map[string]bool) [][]int {
-	if len(nums) == 0 {
-		return subsets
-	}
-	newSubsets := [][]int{}
-	for _, set := range subsets {
-		newSet := append(set, nums[0])
-		if _, ok := subsetsMap[fmt.Sprint(newSet)]; ok {
-			continue
-		}
-		subsetsMap[fmt.Sprint(newSet)] = true
-		newSubsets = append(newSubsets, newSet)
-	}
-	return subsetsWithDupIter(nums[1:], append(subsets, newSubsets...), subsetsMap)
-}
-
 func subsetsWithDup(nums []int) [][]int {
 func subsetsWithDup(nums []int) [][]int {
 	sort.Ints(nums)
 	sort.Ints(nums)
 	subsets := [][]int{[]int{}}
 	subsets := [][]int{[]int{}}
-	subsetsMap := make(map[string]bool, 0)
-	result := subsetsWithDupIter(nums, subsets, subsetsMap)
-	sort.Sort(Int2DSlice(result))
-	fmt.Println(subsetsMap)
-	return result
-}
-
-func testSubsetsWithDup(nums []int) {
-	subsets := subsetsWithDup(nums)
-	fmt.Println("\nThe subsets of", nums, "is", subsets)
+	for i, cnt := 0, 0; i < len(nums); i += cnt {
+		for cnt = 1; cnt+i < len(nums) && nums[cnt+i] == nums[i]; cnt++ {
+			// count the number of same elements
+		}
+		preLen := len(subsets)
+		for j := 0; j < preLen; j++ {
+			subset := make([]int, len(subsets[j]))
+			copy(subset, subsets[j]) // deep copy, not create slice (!!!)
+			for k := 0; k < cnt; k++ {
+				subset = append(subset, nums[i])
+				subsets = append(subsets, subset)
+			}
+		}
+	}
+	return subsets
 }
 }
 
 
-func main() {
-	nums := []int{1, 2, 2, 1, 2, 3, 5, 7, 2}
-	testSubsetsWithDup(nums)
-}
+// func main() {
+// 	nums := []int{1, 2, 2, 3, 4}
+// 	fmt.Println(subsetsWithDup(nums))
+// }

+ 4 - 2
medium/91.go

@@ -1,10 +1,12 @@
 package main
 package main
 
 
+import "fmt"
+
 func numDecodings(s string) int {
 func numDecodings(s string) int {
 	return 0
 	return 0
 }
 }
 
 
-/* func main() {
+func main() {
 	str := "12432546"
 	str := "12432546"
 	fmt.Println(numDecodings(str))
 	fmt.Println(numDecodings(str))
-} */
+}