q5/listhead.go
aozhiwei a6abd190f9 1
2024-04-07 14:32:38 +08:00

138 lines
2.3 KiB
Go

package q5
type ListHead_Foreach_Func func(interface{}) bool
type ListHead struct {
next *ListHead
prev *ListHead
data interface{}
}
func (this *ListHead) Init(data interface{}) {
this.next = this
this.prev = this
this.data = data
}
func (this *ListHead) GetData() interface{} {
return this.data
}
func (this *ListHead) Del() {
this.next.prev = this.prev
this.prev.next = this.next
}
func (this *ListHead) AddTail(pnew *ListHead) {
prev := this.prev
next := this
next.prev = pnew
pnew.next = next
pnew.prev = prev
prev.next = pnew
}
func (this *ListHead) AddHead(pnew *ListHead) {
prev := this
next := this.prev
next.prev = pnew
pnew.next = next
pnew.prev = prev
prev.next = pnew
}
func (this *ListHead) FirstEntry() interface{} {
if !this.next.isCursor() {
return this.next.data
}
for pos := this.next; pos != this; pos = pos.next {
if !pos.isCursor() {
return pos.data
}
}
return nil
}
func (this *ListHead) Replace(pnew *ListHead) {
pnew.next = this.next
pnew.next.prev = pnew
pnew.prev = this.prev
pnew.prev.next = pnew
}
func (this *ListHead) ReplaceInit(pnew *ListHead) {
this.Replace(pnew)
this.next = this
this.prev = this
}
func (this *ListHead) Empty() bool {
if this.next == this {
return true
}
if !this.next.isCursor() {
return false
}
for pos := this.next; pos != this; pos = pos.next {
if !pos.isCursor() {
return false
}
}
return true
}
func (this *ListHead) DelInit() {
this.Del()
this.next = this
this.prev = this
}
func (this *ListHead) Size() int32 {
num := int32(0)
this.ForEach(
func(data interface{}) bool {
num++
return true
})
return num
}
func (this *ListHead) isCursor() bool {
return this.data == this
}
func (this *ListHead) IsFirst(entry* ListHead) bool {
return this.next == entry
}
func (this *ListHead) ForEach(cb ListHead_Foreach_Func) {
for pos := this.next; pos != this; pos = pos.next {
if !cb(pos.data) {
break
}
}
/*
cursor := ListHead{}
cursor.data = &cursor
this.AddHead(&cursor)
defer cursor.Del()
for cursor.next != this {
oldN := cursor.next
if !cursor.next.isCursor() && !cb(cursor.next.data) {
break
}
if cursor.next == oldN {
oldN.Del()
cursor.AddTail(oldN)
}
}*/
}
func NewListHead() *ListHead {
l := new(ListHead)
l.Init(nil)
return l
}