package aoc type Queue[T comparable] struct { items []T } func NewQueue[T comparable](items []T) *Queue[T] { return &Queue[T]{ items: items, } } func (q *Queue[T]) Len() int { return len(q.items) } func (q *Queue[T]) Push(item T) { q.items = append(q.items, item) } func (q *Queue[T]) Pop() T { var x T x, q.items = q.items[len(q.items)-1], q.items[:len(q.items)-1] return x } func (q *Queue[T]) Unshift(item T) { q.items = append([]T{item}, q.items...) } func (q *Queue[T]) Shift() T { var x T x, q.items = q.items[0], q.items[1:] return x } func (q *Queue[T]) Append(items []T) { q.items = append(q.items, items...) } func (q *Queue[T]) Copy() *Queue[T] { ret := &Queue[T]{ items: make([]T, len(q.items)), } copy(ret.items, q.items) return ret } func (q *Queue[T]) Cut(at, count int) []T { ret := q.items[at : at+count] q.items = append(q.items[:at], q.items[at+count:]...) return ret } func (q *Queue[T]) Delete(item T) { for i := range q.items { if q.items[i] == item { q.items = append(q.items[:i], q.items[i+1:]...) return } } } func (q *Queue[T]) Expand(at, by int) { q.items = append(q.items[:at], append(make([]T, by), q.items[at:]...)...) } func (q *Queue[T]) Extend(by int) { q.items = append(q.items, make([]T, by)...) } func (q *Queue[T]) FilterInPlace(keep func(item T) bool) { n := 0 for _, x := range q.items { if keep(x) { q.items[n] = x n++ } } q.items = q.items[:n] } func (q *Queue[T]) Insert(item T, location int) { q.InsertVector([]T{item}, location) } func (q *Queue[T]) InsertVector(items []T, location int) { q.items = append(q.items[:location], append(items, q.items[location:]...)...) }