• go面试题 腐烂的苹果(橘子、水果)


    题目:给定一个n \times m的网格,其中每个单元格中可能有三种值。分别是0,1,2。

    0表示这个格子为空,1表示这个格子有一个完好的苹果,2表示这个格子有一个腐烂的苹果。

    腐烂的苹果每分钟会向上下左右四个方向的苹果传播一次病菌,并导致相邻的苹果腐烂。请问经过多少分钟,网格中不存在完好的苹果。如果有苹果永远不会腐烂则返回-1。

    数据范围:1 \leq n , m \leq 100 , 网络中的值满足0  \leq  val  \leq 2

     测试用例:

    1. 用例1
    2. 输入:[[2,1,1],[1,1,0],[0,1,1]]
    3. 输出:4
    4. 用例2
    5. 输入:[[2,1,1],[1,0,1],[1,1,1]]
    6. 输出:4

     题目评价:

    本人是最讨厌这种类型的题目,感觉特别麻烦(本人太菜了)。但这种题目的主流解法有两种:广度优先搜索(BFS)和 队列实现

    解题思路:

    方法一(BFS):

    首先分别将腐烂的橘子和新鲜的橘子保存在两个集合中;

    模拟广度优先搜索的过程,方法是判断在每个腐烂橘子的四个方向上是否有新鲜橘子,如果有就腐烂它。每腐烂一次时间加 11,并剔除新鲜集合里腐烂的橘子;

    当橘子全部腐烂时结束循环

    1. func orangesRotting(grid [][]int) int {
    2. if !hasFresh(grid) {
    3. return 0
    4. }
    5. time := getTimes(grid)
    6. if hasFresh(grid) {
    7. return -1
    8. }
    9. return time
    10. }
    11. func hasFresh(grid [][]int) bool {
    12. for i := range grid {
    13. for _, val := range grid[i] {
    14. if 1 == val {
    15. return true
    16. }
    17. }
    18. }
    19. return false
    20. }
    21. func getTimes(grid [][]int) int {
    22. q := getQueue(grid)
    23. time := 0
    24. for len(q) > 0 {
    25. next := make([][]int, 0)
    26. for i := range q {
    27. row := q[i][0]
    28. col := q[i][1]
    29. next = setRot(grid, next, row-1, col)
    30. next = setRot(grid, next, row, col+1)
    31. next = setRot(grid, next, row+1, col)
    32. next = setRot(grid, next, row, col-1)
    33. }
    34. if len(next) != 0 {
    35. time++
    36. }
    37. q = next
    38. }
    39. return time
    40. }
    41. func getQueue(grid [][]int) [][]int {
    42. q := make([][]int, 0)
    43. for i := range grid {
    44. for j, val := range grid[i] {
    45. if 2 == val {
    46. q = append(q, []int{i, j})
    47. }
    48. }
    49. }
    50. return q
    51. }
    52. func setRot(grid, q [][]int, row, col int) [][]int {
    53. if row < 0 || col < 0 || row >= len(grid) || col >= len(grid[0]) || grid[row][col] != 1 {
    54. return q
    55. }
    56. grid[row][col] = 2
    57. q = append(q, []int{row, col})
    58. return q
    59. }

    方法二( 队列实现):

    1. // 位置结构体
    2. type Pos struct {r,c int}
    3. // 队列
    4. type Queue []Pos
    5. // 入队
    6. func (this *Queue)Push(x Pos) {
    7. (*this) = append(*this,x)
    8. }
    9. // 出队
    10. func (this *Queue)Pop() Pos {
    11. res := (*this)[0]
    12. (*this) = (*this)[1:len(*this)]
    13. return res
    14. }
    15. // 判断队空
    16. func (this Queue)IsEmpty() bool {
    17. if len(this) == 0 {return true}
    18. return false
    19. }
    20. func orangesRotting(grid [][]int) int {
    21. res := -1
    22. n,m := len(grid),len(grid[0])
    23. dir := [][2]int{{1,0},{-1,0},{0,1},{0,-1}} // 方向矢量
    24. num1,num2 := 0,0 // 记录每一层腐烂橘子的数目
    25. flag := false // 记录初始状态下是否含有新鲜橘子
    26. var ql Queue
    27. for i := 0; i < n; i++ {
    28. for j := 0; j < m; j++ {
    29. if grid[i][j] == 2 { // 把第一层腐烂橘子入队并计数
    30. ql.Push(Pos{i,j})
    31. num1++
    32. }
    33. if grid[i][j] == 1 {flag = true}
    34. }
    35. }
    36. if num1 == 0 { // 若没有腐烂的橘子结果取决于有无新鲜的橘子
    37. if flag {return -1}
    38. return 0
    39. }
    40. for !ql.IsEmpty() {
    41. now := ql.Pop()
    42. for i := 0; i < 4; i++ {
    43. r,c := now.r+dir[i][0],now.c+dir[i][1]
    44. if r >= 0 && r < n && c >= 0 && c < m && grid[r][c] == 1 {
    45. grid[r][c] = 2
    46. ql.Push(Pos{r,c})
    47. num2++
    48. }
    49. }
    50. num1--
    51. if num1 == 0 { // 遍历完一层就记一次数
    52. res++
    53. num1 = num2
    54. num2 = 0
    55. }
    56. }
    57. // 判断是否还有新鲜的橘子
    58. for i := 0; i < n; i++ {
    59. for j := 0; j < m; j++ {
    60. if grid[i][j] == 1 {return -1}
    61. }
    62. }
    63. return res
    64. }

    如果还是看不懂,可以看这个力扣网站上面的这道题目,相信对你有所帮助力扣icon-default.png?t=M85Bhttps://leetcode.cn/problems/rotting-oranges/

  • 相关阅读:
    数字 IC 设计职位经典笔/面试题(四)
    巧用@Conditional注解根据配置文件注入不同的bean对象
    13个 Python 必备的知识,建议收藏
    【Mybatis源码分析】插件机制和Pagehelper插件源码分析
    CG MAGIC进行实体渲染后!分析渲染器CR和VR的区别之处!
    演唱会没买到票?VR直播为你弥补遗憾
    Linux -- 面试考点要点,笔试不多
    想用iPhone录视频同时拍照片?这篇教你!附送10个苹果手机技巧
    优化redis key 迁移程序(云原生版本)
    细胞穿膜肽TAT/血管肽Angiopep/靶向多肽cRGD偶联TIO2二氧化钛纳米粒(TiO2-Angiopep)
  • 原文地址:https://blog.csdn.net/MLittlehands/article/details/126909915