程式碼隨想錄day27 || 455 分餅乾,376 擺動序列,53 最大子序列和

周公瑾55發表於2024-08-12

分餅乾

func findContentChildren(g []int, s []int) int {
	// 第一思路,雙指標暴力解法
	var count int
	var used2 = make([]bool, len(s))
	g = quicksort(g)
	s = quicksort(s)
	for _, child := range g {
		for idx, cookie := range s {
			if !used2[idx] && cookie >= child{
				used2[idx] = true
				count++
				break  // 該child分到餅乾就退出迴圈,讓下一個child參與
			}
		}
	}

	return count

}

func quicksort(li []int) []int{
	if len(li) == 0 {
		return nil
	}

	r := rand.New(rand.NewSource(time.Now().Unix()))
	povid := li[r.Intn(len(li))] // 隨機值作為基準

	var left, right, equal []int
	for _, l := range li {
		if l > povid {
			right = append(right, l)
		}else if l < povid {
			left = append(left, l)
		}else {
			equal = append(equal, l)
		}
	}

	left = quicksort(left)
	right = quicksort(right)

	return append(left, append(equal, right...)...)

}

// 必須要排序,不然可能出現最大的餅乾分給需求最小的child,導致後面較大的需求無法滿足
時間 快排nlogn * 2 + n^2  空間 n
func findContentChildren(g []int, s []int) int {
	// 第一思路,另一種寫法
	var count int
	var idxs int
	g = quicksort(g)
	s = quicksort(s)
	for _, child := range g {
		for idxs < len(s) {
			if s[idxs] >= child {
				count++
				idxs++
				break
			}
			idxs++
		}
	}
	return count
}

376 擺動序列

image

func wiggleMaxLength(nums []int) int {
	// 思路 遇到相鄰元素積是0或者負數,計數加一
	if len(nums) == 1 {
		return 1
	}

	var diffpre, diff, count int
	for i := 1; i < len(nums); i++ {
		diff = nums[i] - nums[i - 1]
		if diffpre <= 0 && diff > 0 ||
			diffpre >= 0 && diff < 0 {
			count++
		}
		if diff != 0 { // 出現單調情況再賦值,避免出現情況4也被統計
			diffpre = diff
		}
	}
	return count + 1
}

53 最大子序列和

func maxSubArray(nums []int) int {
	// 分別儲存連續和以及最大和,連續和不斷貪心往後累加,如果大於最大和就更新最大和
	// 連續和更新邏輯,如果目前大於0,往後累加,如果小於0,捨棄,直接等於當前元素

	var sum, maxsum int
	maxsum = math.MinInt
	for _, v := range nums {
		if sum >= 0 {
			sum += v
		}else {
			sum = v
		}

		if sum > maxsum {
			maxsum = sum
		}
	}
	return maxsum
}

相關文章