这个题目有点怪

delaywu · 2021-09-08 16:26:36 · 2002 次点击 · 大约8小时之前 开始浏览    置顶
这是一个创建于 2021-09-08 16:26:36 的主题,其中的信息可能已经有所发展或是发生改变。

package main

import "fmt"

type student struct {
   name string
   age  int
}

func main() {
   m := make(map[string]*student)
   stus := []student{
      {name: "pprof.cn", age: 18},
      {name: "测试", age: 23},
      {name: "博客", age: 28},
   }

   for _, stu := range stus {
      m[stu.name] = &stu
   }
   for k, v := range m {
      fmt.Println(k, "=>", v.name)
   }
}

这段代码为何会显示

image.png


有疑问加站长微信联系(非本文作者)

入群交流(和以上内容无关):加入Go大咖交流群,或添加微信:liuxiaoyan-s 备注:入群;或加QQ群:692541889

2002 次点击  
加入收藏 微博
16 回复  |  直到 2021-09-22 09:58:19
jthmath
jthmath · #1 · 4年之前

先把代码格式化一下

delaywu
delaywu · #2 · 4年之前

@jthmath 麻烦帮我看看

zhang-jianqiang
zhang-jianqiang · #3 · 4年之前

因为你用的指针类型,循环时把stu赋值给一个新变量或者拷贝stu然后取地址就正常了

delaywu
delaywu · #4 · 4年之前
tablecell
tablecell · #5 · 4年之前

够烂面试题不考算法,不考原理,专考这么烂坑的目的是什么? 害怕简历上写的八年golang项目经验全是假的,用烂坑来验证一下

liu-qi-chang
liu-qi-chang · #6 · 4年之前

@delaywu 能解释一下么,大佬说的话我没理解

jinl80
jinl80 · #7 · 4年之前

for i := range stus { m[stu.name] = &stus[i] }

wangameng
wangameng · #8 · 4年之前
liu-qi-changliu-qi-chang #6 回复

@delaywu 能解释一下么,大佬说的话我没理解

stu引用的指针,只会保存最后1个变量的地址

heyHui2018
heyHui2018 · #9 · 4年之前

这个坑还是挺容易踩的,我一直劝身边人用slice[i]而不是_,v的v

zzustu
zzustu · #10 · 4年之前

最好的避坑方法就是:

  1. 要用*都用*
  2. 要不用都不用

一个用一个不用,自己把自己绕迷

// 方式一
m := make(map[string]*student)
stus := []*student{}

for _, stu := range stus {
    m[stu.name] = stu
}

// 方式二
m := make(map[string]student)
stus := []student{}

for _, stu := range stus {
    m[stu.name] = stu
}
eirueirufu
eirueirufu · #11 · 4年之前

这个不是range常见的坑吗,打印下它们的地址,都是一样的

boonbonnpeng
boonbonnpeng · #12 · 4年之前

for _, stu := range stus { m[stu.name] = &amp;stu }</br> 三次循环复用的是同一个stu变量,你对这个stu取指针并赋值到m中,就导致m中三个key映射的都是stu。</br> 在最后一次循环中,stu被赋值为“博客”,所以最后三个key打印出来的都是“博客”。</br> 要解决这个问题,最简单而且不影响原有逻辑的方法是每次循环都定义一个局部变量:</br> for _, stu := range stus { stu := stu m[stu.name] = stu }</br> 或者通过下标访问切片:</br> for i := range stus { m[stus[i].name] = stus[i] }

zdf123456
zdf123456 · #13 · 4年之前

记住不要在for-range中对value和key取地址就好

rustgo20
rustgo20 · #14 · 4年之前

代码不要随便乱写

tablecell
tablecell · #15 · 4年之前

够烂在最常用的基础数据类型上都有这么严重的坑 仍然挡不住码农追捧够烂 真是够烂虐我千百遍,我待够烂如初恋 

zzustu
zzustu · #16 · 4年之前
tablecelltablecell #15 回复

够烂在最常用的基础数据类型上都有这么严重的坑 仍然挡不住码农追捧够烂 真是够烂虐我千百遍,我待够烂如初恋 

阴阳怪气

添加一条新回复 (您需要 登录 后才能回复 没有账号 ?)
  • 请尽量让自己的回复能够对别人有帮助
  • 支持 Markdown 格式, **粗体**、~~删除线~~、`单行代码`
  • 支持 @ 本站用户;支持表情(输入 : 提示),见 Emoji cheat sheet
  • 图片支持拖拽、截图粘贴等方式上传