1
2
3
4
5 package a
6
7 import (
8 "fmt"
9 )
10
11
12 type Element[T any] struct {
13
14
15
16
17
18 next, prev *Element[T]
19
20
21 list *List[T]
22
23
24 Value T
25 }
26
27
28 func (e *Element[T]) Next() *Element[T] {
29 if p := e.next; e.list != nil && p != &e.list.root {
30 return p
31 }
32 return nil
33 }
34
35
36 func (e *Element[T]) Prev() *Element[T] {
37 if p := e.prev; e.list != nil && p != &e.list.root {
38 return p
39 }
40 return nil
41 }
42
43
44
45 type List[T any] struct {
46 root Element[T]
47 len int
48 }
49
50
51 func (l *List[T]) Init() *List[T] {
52 l.root.next = &l.root
53 l.root.prev = &l.root
54 l.len = 0
55 return l
56 }
57
58
59 func New[T any]() *List[T] { return new(List[T]).Init() }
60
61
62
63 func (l *List[_]) Len() int { return l.len }
64
65
66 func (l *List[T]) Front() *Element[T] {
67 if l.len == 0 {
68 return nil
69 }
70 return l.root.next
71 }
72
73
74 func (l *List[T]) Back() *Element[T] {
75 if l.len == 0 {
76 return nil
77 }
78 return l.root.prev
79 }
80
81
82 func (l *List[_]) lazyInit() {
83 if l.root.next == nil {
84 l.Init()
85 }
86 }
87
88
89 func (l *List[T]) insert(e, at *Element[T]) *Element[T] {
90 e.prev = at
91 e.next = at.next
92 e.prev.next = e
93 e.next.prev = e
94 e.list = l
95 l.len++
96 return e
97 }
98
99
100 func (l *List[T]) insertValue(v T, at *Element[T]) *Element[T] {
101 return l.insert(&Element[T]{Value: v}, at)
102 }
103
104
105 func (l *List[T]) remove(e *Element[T]) *Element[T] {
106 e.prev.next = e.next
107 e.next.prev = e.prev
108 e.next = nil
109 e.prev = nil
110 e.list = nil
111 l.len--
112 return e
113 }
114
115
116 func (l *List[T]) move(e, at *Element[T]) *Element[T] {
117 if e == at {
118 return e
119 }
120 e.prev.next = e.next
121 e.next.prev = e.prev
122
123 e.prev = at
124 e.next = at.next
125 e.prev.next = e
126 e.next.prev = e
127
128 return e
129 }
130
131
132
133
134 func (l *List[T]) Remove(e *Element[T]) T {
135 if e.list == l {
136
137
138 l.remove(e)
139 }
140 return e.Value
141 }
142
143
144 func (l *List[T]) PushFront(v T) *Element[T] {
145 l.lazyInit()
146 return l.insertValue(v, &l.root)
147 }
148
149
150 func (l *List[T]) PushBack(v T) *Element[T] {
151 l.lazyInit()
152 return l.insertValue(v, l.root.prev)
153 }
154
155
156
157
158 func (l *List[T]) InsertBefore(v T, mark *Element[T]) *Element[T] {
159 if mark.list != l {
160 return nil
161 }
162
163 return l.insertValue(v, mark.prev)
164 }
165
166
167
168
169 func (l *List[T]) InsertAfter(v T, mark *Element[T]) *Element[T] {
170 if mark.list != l {
171 return nil
172 }
173
174 return l.insertValue(v, mark)
175 }
176
177
178
179
180 func (l *List[T]) MoveToFront(e *Element[T]) {
181 if e.list != l || l.root.next == e {
182 return
183 }
184
185 l.move(e, &l.root)
186 }
187
188
189
190
191 func (l *List[T]) MoveToBack(e *Element[T]) {
192 if e.list != l || l.root.prev == e {
193 return
194 }
195
196 l.move(e, l.root.prev)
197 }
198
199
200
201
202 func (l *List[T]) MoveBefore(e, mark *Element[T]) {
203 if e.list != l || e == mark || mark.list != l {
204 return
205 }
206 l.move(e, mark.prev)
207 }
208
209
210
211
212 func (l *List[T]) MoveAfter(e, mark *Element[T]) {
213 if e.list != l || e == mark || mark.list != l {
214 return
215 }
216 l.move(e, mark)
217 }
218
219
220
221 func (l *List[T]) PushBackList(other *List[T]) {
222 l.lazyInit()
223 for i, e := other.Len(), other.Front(); i > 0; i, e = i-1, e.Next() {
224 l.insertValue(e.Value, l.root.prev)
225 }
226 }
227
228
229
230 func (l *List[T]) PushFrontList(other *List[T]) {
231 l.lazyInit()
232 for i, e := other.Len(), other.Back(); i > 0; i, e = i-1, e.Prev() {
233 l.insertValue(e.Value, &l.root)
234 }
235 }
236
237
238 func Transform[TElem1, TElem2 any](lst *List[TElem1], f func(TElem1) TElem2) *List[TElem2] {
239 ret := New[TElem2]()
240 for p := lst.Front(); p != nil; p = p.Next() {
241 ret.PushBack(f(p.Value))
242 }
243 return ret
244 }
245
246 func CheckListLen[T any](l *List[T], len int) bool {
247 if n := l.Len(); n != len {
248 panic(fmt.Sprintf("l.Len() = %d, want %d", n, len))
249 return false
250 }
251 return true
252 }
253
254 func CheckListPointers[T any](l *List[T], es []*Element[T]) {
255 root := &l.root
256
257 if !CheckListLen(l, len(es)) {
258 return
259 }
260
261
262 if len(es) == 0 {
263 if l.root.next != nil && l.root.next != root || l.root.prev != nil && l.root.prev != root {
264 panic(fmt.Sprintf("l.root.next = %p, l.root.prev = %p; both should both be nil or %p", l.root.next, l.root.prev, root))
265 }
266 return
267 }
268
269
270
271 for i, e := range es {
272 prev := root
273 Prev := (*Element[T])(nil)
274 if i > 0 {
275 prev = es[i-1]
276 Prev = prev
277 }
278 if p := e.prev; p != prev {
279 panic(fmt.Sprintf("elt[%d](%p).prev = %p, want %p", i, e, p, prev))
280 }
281 if p := e.Prev(); p != Prev {
282 panic(fmt.Sprintf("elt[%d](%p).Prev() = %p, want %p", i, e, p, Prev))
283 }
284
285 next := root
286 Next := (*Element[T])(nil)
287 if i < len(es)-1 {
288 next = es[i+1]
289 Next = next
290 }
291 if n := e.next; n != next {
292 panic(fmt.Sprintf("elt[%d](%p).next = %p, want %p", i, e, n, next))
293 }
294 if n := e.Next(); n != Next {
295 panic(fmt.Sprintf("elt[%d](%p).Next() = %p, want %p", i, e, n, Next))
296 }
297 }
298 }
299
View as plain text