Closed DaFeiL closed 2 years ago
请问你看的哪个版本的源吗?我确认一下
感觉你说的是这里:
func growWork(t *maptype, h *hmap, bucket uintptr) {
// make sure we evacuate the oldbucket corresponding
// to the bucket we're about to use
evacuate(t, h, bucket&h.oldbucketmask())
// evacuate one more oldbucket to make progress on growing
if h.growing() {
evacuate(t, h, h.nevacuate)
}
}
是的,这里evacute函数的实现逻辑,就是搬迁了整个buckte及相应的所有overflow bucket代码链接:https://github.com/golang/go/blob/0ed31eb73b13bd57aff727f4ab759c6701d45a01/src/runtime/map.go#L1173-L1247
------------------ 原始邮件 ------------------ 发件人: "Hongcai @.>; 发送时间: 2022年3月24日(星期四) 下午5:21 收件人: @.>; 抄送: @.>; @.>; 主题: Re: [RainbowMango/GoExpertProgramming] [勘误]反馈一个第1章第3节的内容错误 (Issue #102)
感觉你说的是这里: func growWork(t maptype, h hmap, bucket uintptr) { // make sure we evacuate the oldbucket corresponding // to the bucket we're about to use evacuate(t, h, bucket&h.oldbucketmask()) // evacuate one more oldbucket to make progress on growing if h.growing() { evacuate(t, h, h.nevacuate) } }
— Reply to this email directly, view it on GitHub, or unsubscribe. You are receiving this because you authored the thread.Message ID: @.***>
感谢指出,
-考虑到如果map存储了数以亿计的键值对,一次性搬迁将会造成比较大的延时,Go采用逐步搬迁策略,即每次访问map时都会触发一次搬迁,每次搬迁2个键值对。
+考虑到如果map存储了数以亿计的键值对,一次性搬迁将会造成比较大的延时,Go采用逐步搬迁策略,即每次访问map时都会触发一次搬迁,每次搬迁2个bucket。
这么修改了。
PS:你看的网页版不知道是谁维护的 :(, 这个修改将在下次重印时修正。
画红线部分也不准确(网页版),实际扩容条件如下:①当 B 小于 15,也就是 bucket 总数 2^B 小于 2^15 时,如果 overflow 的 bucket 数量超过 2^B;②当 B >= 15,也就是 bucket 总数 2^B 大于等于 2^15,如果 overflow 的 bucket 数量超过 2^15。代码链接:https://github.com/golang/go/blob/0ed31eb73b13bd57aff727f4ab759c6701d45a01/src/runtime/map.go#L1090-L1100
------------------ 原始邮件 ------------------ 发件人: "Hongcai @.>; 发送时间: 2022年3月24日(星期四) 晚上6:07 收件人: @.>; 抄送: @.>; @.>; 主题: Re: [RainbowMango/GoExpertProgramming] [勘误]反馈一个第1章第3节的内容错误 (Issue #102)
感谢指出, -考虑到如果map存储了数以亿计的键值对,一次性搬迁将会造成比较大的延时,Go采用逐步搬迁策略,即每次访问map时都会触发一次搬迁,每次搬迁2个键值对。 +考虑到如果map存储了数以亿计的键值对,一次性搬迁将会造成比较大的延时,Go采用逐步搬迁策略,即每次访问map时都会触发一次搬迁,每次搬迁2个bucket。
这么修改了。
PS:你看的网页版不知道是谁维护的 :(, 这个修改将在下次重印时修正。
— Reply to this email directly, view it on GitHub, or unsubscribe. You are receiving this because you authored the thread.Message ID: @.***>
纸质版目前的表述是:
触发扩容需要满足以下任一条件:
- 负载因子大于6.5时,也即平均每个bucket存储的键值对达到6.5个以上;
- overflow数量达到2^min(15,B)时;
有问题吗?
没有问题,我看得到网页版,以为纸质版是一样的。祝好!
------------------ 原始邮件 ------------------ 发件人: "Hongcai @.>; 发送时间: 2022年3月24日(星期四) 晚上7:31 收件人: @.>; 抄送: @.>; @.>; 主题: Re: [RainbowMango/GoExpertProgramming] [勘误]反馈一个第1章第3节的内容错误 (Issue #102)
纸质版目前的表述是:
触发扩容需要满足以下任一条件: - 负载因子大于6.5时,也即平均每个bucket存储的键值对达到6.5个以上; - overflow数量达到2^min(15,B)时;
有问题吗?
— Reply to this email directly, view it on GitHub, or unsubscribe. You are receiving this because you authored the thread.Message ID: @.***>
再次感谢。
1.18
------------------ 原始邮件 ------------------ 发件人: "Hongcai @.>; 发送时间: 2022年3月24日(星期四) 上午9:06 收件人: @.>; 抄送: @.>; @.>; 主题: Re: [RainbowMango/GoExpertProgramming] [勘误]反馈一个第1章第3节的内容错误 (Issue #102)
请问你看的哪个版本的源吗?我确认一下
— Reply to this email directly, view it on GitHub, or unsubscribe. You are receiving this because you authored the thread.Message ID: @.***>
问题描述 网页版的内容有点小问题
如何找到这个错误
您认为应该如何? map扩容确实是渐进式扩容,但是每次搬迁时并不是搬迁两个键值对,而是尝试搬迁两个bucket 图片
其他补充信息 源代码里面,通过evacuate函数进行实际的搬迁,并且是进行线性遍历,会对与每个bucket及其链接的所有overflow bucket都会进行搬迁,所有并不仅仅是两个键值对