最小步数归零问题&珠子颜色去重| 豆包MarsCode AI刷题

94 阅读5分钟

最小步数归零问题

问题解析

问题描述

小R拿到了一个长度为 n 的数组,其中每个元素都是一个正整数。小R发现每次可以删除某个数组中某个数的一位数字,这样可以逐步将所有数字变为 0。他想知道,要将数组中所有数字都变为 0,最少需要多少步?

输入输出

  • 输入

    • n:数组的长度。
    • a:一个包含 n 个正整数的数组。
  • 输出

    • 一个整数,表示将数组中所有数字都变为 0 所需的最少步数。

测试样例

  • 样例1

    • 输入:n = 5, a = [10, 13, 22, 100, 30]
    • 输出:7
    • 解释:10 需要 1 步,13 需要 2 步,22 需要 2 步,100 需要 1 步,30 需要 1 步,总共 7 步。
  • 样例2

    • 输入:n = 3, a = [5, 50, 505]
    • 输出:4
    • 解释:5 需要 1 步,50 需要 1 步,505 需要 2 步,总共 4 步。
  • 样例3

    • 输入:n = 4, a = [1000, 1, 10, 100]
    • 输出:4
    • 解释:1000 需要 1 步,1 需要 1 步,10 需要 1 步,100 需要 1 步,总共 4 步。

思路解析

1. 遍历数组

遍历数组中的每个数字,对于每个数字,计算将其变为 0 所需的最少步数。

2. 计算步数

对于每个数字,从最低位开始,逐位检查是否为 0。如果某位不为 0,则需要一步将其删除。将数字不断除以 10,直到数字变为 0

3. 累加步数

将每个数字的步数累加,得到最终的总步数。

代码实现

package main

import "fmt"

func solution(n int, a []int) int {
    count := 0
    for i := 0; i < n; i++ {
        t := a[i]
        for t > 0 {
            if t%10 > 0 {
                count++
            }
            t = t / 10
        }
    }
    return count
}

func main() {
    fmt.Println(solution(5, []int{10, 13, 22, 100, 30}) == 7)
    fmt.Println(solution(3, []int{5, 50, 505}) == 4)
    fmt.Println(solution(4, []int{1000, 1, 10, 100}) == 4)
}

代码解析

  1. 初始化

    • count:用于记录总步数。
  2. 遍历数组

    • 使用 for i := 0; i < n; i++ 遍历数组 a
  3. 计算步数

    • 对于每个数字 t,使用 for t > 0 循环,逐位检查是否为 0
    • 如果 t%10 > 0,则需要一步将其删除,count 加1。
    • 将 t 除以 10,继续检查下一位。
  4. 返回结果

    • 返回 count,表示将数组中所有数字都变为 0 所需的最少步数。

总结

通过上述方法,我们可以高效地计算出将数组中所有数字都变为 0 所需的最少步数。该方法的时间复杂度为 O(n * m),其中 n 是数组的长度,m 是数字的最大位数。这种方法在处理大规模数据时也能保持较高的效率。

珠子颜色去重

问题解析

问题描述

小S拥有一条由 n 颗珠子组成的手链,每颗珠子都有一个对应的颜色编号。她希望将手链上相同颜色的珠子进行去重,只保留每种颜色最后出现的那颗珠子,同时保持珠子原来的相对顺序。

输入输出

  • 输入

    • n:珠子的数量。
    • a:一个包含 n 个整数的数组,表示每颗珠子的颜色编号。
  • 输出

    • 一个整数数组,表示去重后的珠子颜色编号,保持原来的相对顺序。

测试样例

  • 样例1

    • 输入:n = 8, a = [1, 2, 1, 3, 4, 2, 4, 4]
    • 输出:[1, 3, 2, 4]
    • 解释:颜色 1 最后出现在索引 2,颜色 2 最后出现在索引 5,颜色 3 最后出现在索引 3,颜色 4 最后出现在索引 7
  • 样例2

    • 输入:n = 5, a = [5, 5, 5, 5, 5]
    • 输出:[5]
    • 解释:颜色 5 最后出现在索引 4
  • 样例3

    • 输入:n = 6, a = [6, 1, 2, 6, 1, 2]
    • 输出:[6, 1, 2]
    • 解释:颜色 6 最后出现在索引 3,颜色 1 最后出现在索引 4,颜色 2 最后出现在索引 5

思路解析

1. 记录最后一次出现的索引

使用一个 map 记录每种颜色最后出现的索引。

2. 遍历数组

遍历数组,检查当前颜色是否是最后一次出现。如果是,则将其添加到结果数组中。

代码实现

package main

import (
	"fmt"
	"reflect"
)

func solution(n int, a []int) []int {
	last := map[int]int{}
	
	// 记录每种颜色最后出现的索引
	for i := 0; i < n; i++ {
		last[a[i]] = i
	}
	
	res := []int{}
	
	// 遍历数组,只保留每种颜色最后出现的那颗珠子
	for i := 0; i < n; i++ {
		if last[a[i]] == i {
			res = append(res, a[i])
		}
	}
	
	return res
}

func main() {
	fmt.Println(reflect.DeepEqual(solution(8, []int{1, 2, 1, 3, 4, 2, 4, 4}), []int{1, 3, 2, 4}))
	fmt.Println(reflect.DeepEqual(solution(5, []int{5, 5, 5, 5, 5}), []int{5}))
	fmt.Println(reflect.DeepEqual(solution(6, []int{6, 1, 2, 6, 1, 2}), []int{6, 1, 2}))
}

代码解析

  1. 记录最后一次出现的索引

    • 使用 map 记录每种颜色最后出现的索引。
    • 遍历数组 a,将每个颜色的最后出现索引记录在 last 中。
  2. 遍历数组

    • 再次遍历数组 a,检查当前颜色是否是最后一次出现。
    • 如果是,则将其添加到结果数组 res 中。
  3. 返回结果

    • 返回结果数组 res,表示去重后的珠子颜色编号,保持原来的相对顺序。

总结

通过上述方法,我们可以高效地实现去重操作,并保持珠子原来的相对顺序。该方法的时间复杂度为 O(n),其中 n 是珠子的数量。这种方法在处理大规模数据时也能保持较高的效率。