Table of contents
Topic: Rolling and dividing method (finding the greatest common divisor)
Topic link: LeetCode-1979. Find the greatest common divisor of an array
Analysis of ideas: tossing and dividing method (also called Euclidean algorithm)gcd(a,b) = gcd(b,a mod b)
The core part of the rolling and dividing method is: if r is the remainder of a ÷ b, then gcd(a, b)=gcd(b, r)
Complexity: Time complexity O ( n + log ( max ) ) O(n+log(max))O ( n+l o g ( max x )) , space complexityO ( 1 ) O(1)O(1)
Go code
func findGCD(nums []int) int {
max, min := getMaxMin(nums)
return getGcd(max, min)
}
// gcd求最大公约数
func getGcd(a int, b int) int {
yu := 0
for b != 0 {
yu = a % b //得到余数
a = b //根据辗转相除法,把被除数赋给除数
b = yu //余数赋给被除数
}
return a //返回除数
}
func getMaxMin(nums []int) (max int, min int) {
max, min = nums[0], nums[0]
length := len(nums)
for i:=1; i<length; i++ {
if nums[i] > max {
max = nums[i]
}
if nums[i] < min {
min = nums[i]
}
}
return
}
Question: Check if a number is prime
Idea analysis: To judge whether n is a prime number, you only need to test all possible factors from 2 to sqrtN + "6K +1/-1" rule
Complexity: Time complexity O ( sqrt ( n ) ) O(sqrt(n))O ( s q r t ( n )) , space complexityO ( 1 ) O(1)O(1)
Go code
func isPrimes(n int) bool {
if n <= 1 {
return false
}
if n <= 3 {
return true
}
if n%2==0 || n%3==0 {
return false
}
// 判断n是否是素数时,只需要测试 2 到 sqrtN 的所有可能因子
// max := int(math.Pow(float64(n), 0.5))
max := int(math.Sqrt(float64(n)))
// 根据 "6K +1/-1" 规则
for i:=5; i<=max; i+=6 {
// i+2 正好是 "6K +1/-1" 中的一个值
if n % i == 0 || n%(i+2) == 0 {
return false
}
}
return true
}
Subject: Esperanto sieve
Topic link: LeetCode-204. Counting prime numbers
Analysis of ideas: the idea of Esperanza's sieve method, gradually eliminate the numbers that are not prime numbers
If x is a prime number, then the multiples of x greater than x, 2x, 3x,... must not be prime numbers.
Complexity: Time complexity O ( nloglogn ) O(n log log n)O ( n l o g l o g n ) , space complexityO ( n ) O(n)O ( n )
- Time complexity analysis:
- The number of iterations of the outer loop is n-2, which is O ( n ) O(n)O ( n ) times.
- The number of iterations of the inner loop is in the case of a prime number, starting from i*i, increasing i each time until n. This is because multiples less than i have previously been marked as non-prime. The number of iterations of the inner loop is approximately n/i, where i is a prime number. Therefore, the total number of iterations is n/2 + n/3 + n/5 + ..., and this sum is O ( nloglogn ) O(n log log n)O ( n log log n ) . _ _ _ _
Go code
func countPrimes(n int) int {
count := 0
isNotPrimes := make([]bool, n)
for i:=2; i<n; i++ {
if !isNotPrimes[i] {
count++
for j:=i*i; j<n; j+=i {
isNotPrimes[j] = true
}
}
}
return count
}
Or the following language is clearer, but O ( n ) O(n)O ( n ) time complexity
func countPrimes(n int) (count int) {
isPrimies := make([]bool, n)
for i, _ := range isPrimies {
isPrimies[i] = true
}
for i:=2; i<n; i++ {
// 从2开始已经把2的所有倍数标记为false,3也是,所以剩下的未标记的都是质数
if isPrimies[i] {
count++
// 直接从i*i开始标记,因为2i,3i...这些数一定在i之前就被其他数的倍数标记过了,例如2的所有倍数,3的所有倍数等
for j:=i*i; j<n; j+=i {
isPrimies[j] = false
}
}
}
return
}
Topic: Judging whether it is an ugly number
Topic link: LeetCode-263. Ugly numbers
Idea analysis: cycle division 2 3 5 to determine whether the final value == 1
Complexity: time complexity O ( logn ) O(log n)O ( l o g n ) , space complexityO ( 1 ) O(1)O(1)
- Time complexity: depends on the number of times n is divided by 2 3 5, since n is divided by at least 2 each time, the number of division operations will not exceed O ( logn ) O(log n)O(logn)
Go code
func isUgly(n int) bool {
if n < 1 {
return false
}
if n == 1 {
return true
}
arr := [3]int{
2,3,5}
for _, v := range arr {
for n%v == 0 {
n = n/v
}
}
return n == 1
}