Implementation of sword finger offer go version Chapter 6: various abilities in interview

Posted by podarum on Mon, 17 Jan 2022 10:14:54 +0100

Main purpose of this chapter

This chapter mainly practices communication ability, learning ability, knowledge transfer ability, abstract modeling ability, etc. This requires a solid mathematical foundation. If not, I believe many people will read a problem for a long time like me. To understand it, we need to use video and draw pictures. This is a congenital deficiency and deformity. It is a hard injury brought by our business oriented and search programming. This topic will not be too difficult, but it has the need to use your brain. If necessary, I suggest reading the original text.

Officially start Chapter 6

Interview question 38: number of times a number appears in a sorted array

leetcode-cn.com/problems/zai-pai-x...
Counts the number of times a number appears in the sorted array

func search(nums []int, target int) int {
    //start := 0
    //end := len(nums) - 1
    //for i := 0; i < len(nums); i++ {
    //    if nums[i] == target {
    //        start = i
    //        break
    //    }
    //}
    //if start == -1 || start == len(nums) || nums[start] != target {
    //    return 0
    //}
    //for i := 0; i < len(nums); i++ {
    //    if nums[i] > target {
    //        end = i - 1
    //    }
    //}
    //fmt.Println(start,end)
    //return end - start + 1

    //count := 0
    //for i := 0; i < len(nums); i++ {
    //    if nums[i] == target {
    //        count++
    //    }
    //}
    //return count

    //Highest efficiency
    leftmost := sort.SearchInts(nums, target)
    if leftmost == len(nums) || nums[leftmost] != target {
        return 0
    }
    rightmost := sort.SearchInts(nums, target+1) - 1
    return rightmost - leftmost + 1
}

This is the reference code given by the original text in the textbook, rewritten by C + +

func search(nums []int, target int) int {
    count := 0
    if len(nums) == 0 {
        return count
    }
    first := getFirstTargetIndex(nums, target, 0, len(nums)-1)
    last := getLastTargetIndex(nums, target, 0, len(nums)-1)
    if first > -1 && last > -1 {
        count = last - first + 1
    }
    return count
}

func getFirstTargetIndex(nums []int, target, start, end int) int {
    if start > end {
        return -1
    }
    mid := (start + end) / 2
    fmt.Println(mid, start, end)
    midData := nums[mid]
    if midData > target {
        end = mid - 1
    } else if nums[mid] < target {
        start = mid + 1
    } else {
        if (mid > 0 && nums[mid-1] != target) || mid == 0 {
            return mid
        } else {
            end = mid - 1
        }
    }
    return getFirstTargetIndex(nums, target, start, end)
}
func getLastTargetIndex(nums []int, target, start, end int) int {
    if start > end {
        return -1
    }
    mid := (start + end) / 2
    midData := nums[mid]
    if midData > target {
        end = mid - 1
    } else if nums[mid] < target {
        start = mid + 1
    } else {
        if (mid < len(nums)-1 && nums[mid+1] != target) || mid == len(nums)-1 {
            return mid
        } else {
            start = mid + 1
        }
    }
    return getLastTargetIndex(nums, target, start, end)
}

It's all cream. It's worth seeing.

Interview question 39: depth of binary tree

leetcode-cn.com/problems/er-cha-sh...

type TreeNode struct {
    Val   int
    Left  *TreeNode
    Right *TreeNode
}

func maxDepth(root *TreeNode) int {
    if root == nil {
        return 0
    }
    fmt.Println(root.Val)
    left := maxDepth(root.Left)
    right := maxDepth(root.Right)
    if left > right {
        return left + 1
    } else {
        return right + 1
    }
}
//Judge whether it is a balanced binary tree
func isBalanced(root *TreeNode) bool {
   if root == nil {
      return true
  }
   fmt.Println(root.Val)
   left := maxDepth(root.Left)
   right := maxDepth(root.Right)
   diff := left - right
   if diff > 1 || diff < -1 {
      return false
  }
   return isBalanced(root.Left) && isBalanced(root.Right)
}

Balanced binary tree is the divergence given on the tree. It can also calculate the depth according to the balanced binary tree, and it will avoid repeatedly traversing nodes.

Interview question 40: numbers that appear once in the array

leetcode-cn.com/problems/shu-zu-zh...
In an integer array nums, all but two numbers appear twice. Please write a program to find these two numbers that only appear once. The time complexity is O(n) and the space complexity is O(1).

// Inefficient implementation
func singleNumbers(nums []int) []int {
    if len(nums) == 0 {
        return nil
    }
    sort.Ints(nums)
    fmt.Println(nums)
    result := make([]int, 0)
    if len(nums) == 1 {
        result = append(result, nums[0])
    }
    if nums[0] != nums[1] {
        result = append(result, nums[0])
    }
    if len(nums) > 1 && nums[len(nums)-2] != nums[len(nums)-1] {
        result = append(result, nums[len(nums)-1])
    }
    for i := 1; i < len(nums)-1; i++ {
        if nums[i] != nums[i-1] && nums[i] != nums[i+1] {
            result = append(result, nums[i])
        }
    }
    return result
}

// The title defines that there must be two numbers once, and the other two times
// Grouping XOR
func singleNumbers(nums []int) []int {
   if len(nums) == 0 {
      return nil
  }
   result := make([]int, 2)
   ret := 0
  for _, v := range nums {
      ret ^= v
   }
   div := 1
  for (div & ret) == 0 {
      div <<= 1
  }
   for _, v := range nums {
      if (div & v) != 0 {
         result[0] ^= v
      } else {
         result[1] ^= v
      }
   }

   return result
}

Interview question 41-1: and are two numbers of S

leetcode-cn.com/problems/he-wei-sd...
Enter an incrementally sorted array and a number s, and find two numbers in the array so that their sum is exactly s. If the sum of multiple pairs of numbers is equal to s, any pair can be output.

func twoSum(nums []int, target int) []int {
    if len(nums) == 0 {
        return nil
    }
    result := make([]int, 0)
    left := 0
    right := len(nums) - 1
    for left <= right {
        if nums[left]+nums[right] == target {
            result = append(result, []int{nums[left], nums[right]}...)
            break
        } else if nums[left]+nums[right] > target {
            right--
        } else {
            left++
        }
    }
    return result
}

Interview question 41-2: continuous positive sequence with sum s

leetcode-cn.com/problems/he-wei-sd...
Enter a positive integer target and output a sequence of consecutive positive integers with a sum of target (at least two numbers).
The numbers in the sequence are arranged from small to large, and different sequences are arranged from small to large according to the first number

//Double pointer
func findContinuousSequence(target int) [][]int {
    result := make([][]int, 0)
    if target < 3 {
        return nil
    }
    small, big, middle := 1, 2, (1+target)/2
    curSum := small + big
    for small < middle {
        if curSum == target {
            result = append(result, addSeq(small, big))
        }
        for curSum > target && small < middle {
            curSum -= small
            small++
            if curSum == target {
                result = append(result, addSeq(small, big))
            }
        }
        big++
        curSum += big
    }

    return result
}

func addSeq(small, big int) (result []int) {
    for i := small; i <= big; i++ {
        result = append(result, i)
    }
    return
}

Interview question 42-1: reverse word order

leetcode-cn.com/problems/fan-zhuan...
Input an English sentence and flip the order of words in the sentence, but the order of characters in the word remains the same. For simplicity, punctuation is treated like ordinary letters. For example, enter the string "I am a student ", then output" student a am I”.

func reverseWords(s string) string {
    split := strings.Split(s, " ")
    var res []string
    for i := len(split) - 1; i >= 0; i-- {
        if split[i] != ""{
            res = append(res, split[i])
        }
    }
    fmt.Println(res)
    return strings.Join(res, " ")
}

Interview question 42-2: left rotation string

leetcode-cn.com/problems/zuo-xuan-...
The left rotation operation of a string is to transfer several characters in front of the string to the end of the string.
Please define a function to realize the function of string left rotation operation. For example, if you enter the string "abcdefg" and the number 2, the function will return the result "cdefgab" obtained by rotating two bits left.

func reverseLeftWords(s string, n int) string {
    //Boundary conditions can be determined without judgment
    //res := make([]uint8, len(s), len(s))
    //for i := 0; i < len(s); i++ {
    //    res[i] = s[i]
    //}
    s1 := s[:n]
    s2 := s[n:]
    return s2 + s1
}

Interview question 43: points of n dice

leetcode-cn.com/problems/nge-tou-z...
Throw n dice on the ground, and the sum of points on the upward side of all dice is s. Enter n to print out the probability of occurrence of all possible values of S. You need to use an array of floating-point numbers to return the answer, in which the i-th element represents the probability of the i-th smallest in the set of points that the N dice can roll.

//The reference is written in the way of Java code implementation. It should be simpler in this textbook. In fact, the principle is the same
func dicesProbability(n int) []float64 {
    if n < 1 {
        return nil
    }
    dp := make([][]float64, n)
    for i := range dp {
        dp[i] = make([]float64, (i+1)*6-i)
    }
    for i := range dp[0] {
        dp[0][i] = float64(1) / float64(6)
    }
    for i := 1; i < len(dp); i++ {
        for j := range dp[i-1] {
            for k := range dp[0] {
                dp[i][j+k] += dp[i-1][j] * dp[0][k]
            }
        }
    }
    return dp[n-1]
}

Interview question 44: shunzi in playing cards

leetcode-cn.com/problems/bu-ke-pai...
Draw 5 cards randomly from several pairs of playing cards to judge whether it is a surplus, that is, whether the 5 cards are continuous. 2 ~ 10 is the number itself, a is 1, J is 11, Q is 12, K is 13, and DA and Xiao Wang are 0, which can be regarded as any number. A cannot be regarded as 14.

func isStraight(nums []int) bool {
    if len(nums) != 5 {
        return false
    }
    //1. Order first
    sort.Ints(nums)
    //2. Number of records 0
    zeroNum := 0
    for i := 0; i < len(nums); i++ {
        if nums[i] == 0 {
            zeroNum++
        }
    }
    //fmt.Println(zeroNum)
    //3. Judge whether it can form a shunzi
    for i := zeroNum; i < len(nums)-1; i++ {
        //fmt.Println(nums[i], nums[i+1])
        if nums[i+1] == nums[i] { //If there are equal, return false directly
            return false
        } else if nums[i+1]-nums[i] > 1 {
            //fmt.Println(nums[i], nums[i+1])
            zeroNum -= nums[i+1] - nums[i] - 1
            if zeroNum < 0 {
                return false
            }
        }
    }
    return true
}

Interview question 45: the last number left in the circle

leetcode-cn.com/problems/yuan-quan...
The N numbers 0,1, ···, n-1 are arranged in a circle, starting from the number 0, and the m-th number is deleted from the circle each time (counting from the next number after deletion). Find the last number left in the circle. For example, the five numbers 0, 1, 2, 3 and 4 form a circle. Starting from the number 0, delete the third number each time, then the first four deleted numbers are 2, 0, 4 and 1 in turn, so the last remaining number is 3.
Rules, reading books, I can't push it out at this level

func lastRemaining(n int, m int) int {
    if n < 1 || m < 1 {
        return -1
    }
    last := 0
    for i := 2; i <= n; i++ {
        last = (last + m) % i
    }

    return last
}

Interview question 46: find 1 + 2 +... + n

leetcode-cn.com/problems/qiu-12n-l...
For 1 + 2 +... + n, it is required that keywords such as multiplication and division, for, while, if, else, switch, case and conditional judgment statements (A?B:C) cannot be used.

//It seems that I can only think of recursion
func sumNums(n int) int {
   if n == 0 {
      return 0
  }
   return n + sumNums(n-1)
}

Interview question 47: addition without addition, subtraction, multiplication and division

leetcode-cn.com/problems/bu-yong-j...
Write a function and find the sum of two integers. It is required that four operation symbols "+", "-", "*", "/" shall not be used in the function body.

//There is no other way except bit operation, but leetcode can't detect other symbols
func add(a int, b int) int {
    sum, carry := 0, 0
    for b != 0 {
        sum = a ^ b
        carry = (a & b) << 1
        a = sum
        b = carry
    }
    return a
}

Interview question 48: classes that cannot be inherited

It is not suitable for Go language. Without this statement, can we still realize structures that cannot be inherited?

Summary

It can be seen from this time that the most difficult thing is abstract modeling. As for divergent thinking, it's easy to understand, at least one. It's good to see others. This question is not very difficult. For a few questions, there may be no ideas. You need to look at the answer analysis to write the code. It depends more on self-consciousness to write according to the requirements. The tool detection of leetcode is not so perfect. I suggest you read the original text. The knowledge posted here is to record that I practice in stages. Break down the task. I believe there are few people who just stick to it. In Chapter 7, I suggest and strongly recommend reading the original text, because the focus is not on the title, but on the description and intention of the original text. go func add(a int, b int) int { sum, carry := 0, 0 for b != 0 { sum = a ^ b carry = (a & b) << 1 a = sum b = carry } return a }

Topics: Go Algorithm