golang 切片扩容避坑——底层数组变更

    知识点:切片经过n次append,当某次append元素时,计算出的切片需占用长度超过当前容量,会发生扩容,创建新的底层数组,append函数返回的是 指向新底层数组的新切片 。
    
    避坑:切片扩容后,新创建底层数组,元素拷贝到新的存储地址,使用扩容前获取到的元素指针做更新操作,实际更新的旧底层数组旧切片, 不会更新到新切片中,应使用元素在切片中的索引进行更新。
    
    场景举例:给定切片s1存储n1个struct元素,切片s2存储n2个struct元素,strName="a"。要求:重新计算s1中Name==strName的元素的Age值(假设计算Age需等到第1步完成才能计算)
        1.  将s2的元素存储到s1中。
        2.  根据某算法计算oPerson.Age,并更新到切片中的此元素


    错误实现:

package main

import "fmt"

type Person struct {
    Name string
    Age  int
}

func CulAget() int {
    return 18
}
func main() {
    var s1 = []Person{
        {
            Name: "a",
            Age:  10,
        },
        {
            Name: "b",
            Age:  11,
        },
        {
            Name: "c",
            Age:  12,
        },
    }

    var s2 = []Person{
        {
            Name: "d",
            Age:  13,
        },
        {
            Name: "e",
            Age:  13,
        },
    }

    var strName = "a"
    var oPerson *Person
    for i, tmp := range s1 {
        if tmp.Name == strName {
            oPerson = &s1[i]
            break
        }
    }

    for _, oPerson2 := range s2 {
        s1 = append(s1, oPerson2)
    }

    oPerson.Age = CulAget()
    fmt.Println(oPerson) //&{a 18}
    fmt.Println(s1)      //[{a 10} {b 11} {c 12} {d 13} {e 13}]
}


 正确实现:获取到符合要求的元素所在切片中的索引,根据索引更新切片对应位置的元素
 

package main

import "fmt"

type Person struct {
    Name string
    Age  int
}

func CulAget() int {
    return 18
}

func main() {
    var s1 = []Person{
        {
            Name: "a",
            Age:  10,
        },
        {
            Name: "b",
            Age:  11,
        },
        {
            Name: "c",
            Age:  12,
        },
    }

    var s2 = []Person{
        {
            Name: "d",
            Age:  13,
        },
        {
            Name: "e",
            Age:  13,
        },
    }

    var strName = "a"
    var index int = 0
    for i, tmp := range s1 {
        if tmp.Name == strName {
            index = i
            break
        }
    }

    for _, oPerson2 := range s2 {
        s1 = append(s1, oPerson2)
    }

    s1[index].Age = CulAget()
    fmt.Println(s1) //[{a 18} {b 11} {c 12} {d 13} {e 13}]
}


 

  • 1
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 1
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论 1
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值