引言
在之前的文章Go中的双向链表list的使用与从源码分析:Go中的双线链表list,我们一起看了Go中的容器list的使用与其源码的实现原理,这一次,我们来看一下另一个容器,也就是标题中所述的ring
,Go中的环形链表,与container/list
一样,ring
同样位于包conatainer
中。
数据结构
还是老规矩,一开始先看一下ring中所使用的数据结构。其实ring中使用的结构比较少,只有一个叫做Ring
的结构体。
// 一个Ring是一个环形链表的元素,对于环而言,并不存在起始点或者终止点。
// 指向环中任一元素的指针都用作整个环的引用
// nil环指针指向空的环,对于环来说0值是一个只有一个nil元素的一个元素的环
type Ring struct {
// 分别指向下一个元素与上一个元素
next, prev *Ring
// 该元素内实际存储的数据
Value interface{
} // for use by client; untouched by this library
}
创建实例与初始化的方法
接下来是如何创建一个ring的实例与环的初始化方法
// 创建新的长度为n的ring实例的方法
func New(n int) *Ring {
// 如果输入的n为小于零的负数,则直接返回nil
if n <= 0 {
return nil
}
// 首先创建一个Ring的实例r,并将指针p指向r
r := new(Ring)
p := r
// 从1到n - 1循环,创建n - 1个Ring的实例,并依次将其接起来
for i := 1; i < n; i++ {
// 这里,创建了一个Ring的实例,创建时将新的实例的prev指向当前节点(等号后部分),并将当前节点p的next指针指向了新创建的节点(等号前的部分)
p.next = &Ring{
prev: p}<