From cd3878d6986efcad47a0323c2a79778c133e5056 Mon Sep 17 00:00:00 2001 From: Gregory Date: Wed, 15 Dec 2021 23:35:58 +0200 Subject: [PATCH] generic queue --- fundamentals/queue/queue.go | 35 ++++++++++++++------------------ fundamentals/queue/queue_test.go | 6 +++--- go.mod | 2 +- 3 files changed, 19 insertions(+), 24 deletions(-) diff --git a/fundamentals/queue/queue.go b/fundamentals/queue/queue.go index 519e482..d485d89 100644 --- a/fundamentals/queue/queue.go +++ b/fundamentals/queue/queue.go @@ -1,37 +1,32 @@ package queue -// "Generic" item. -// When type parameters will land this type became -// type Item[T any] T -type Item interface{} - -type Queue interface { - Enqueue(Item) - Dequeue() Item +type Queue[T any] interface { + Enqueue(T) + Dequeue() T Size() int IsEmpty() bool } // We use linked list as internal data structure // to get O(1) speed for push and pop opeartions -type node struct { +type node[Item any] struct { item Item - next *node + next *node[Item] } -type queue struct { +type queue[OfType any] struct { size int - head *node - tail *node + head *node[OfType] + tail *node[OfType] } -func NewQueue() Queue { - return &queue{} +func NewQueue[OfType any]() Queue[OfType] { + return &queue[OfType]{} } -func (q *queue) Enqueue(item Item) { +func (q *queue[T]) Enqueue(item T) { oldTail := q.tail - q.tail = &node{item: item, next: nil} + q.tail = &node[T]{item: item, next: nil} if q.IsEmpty() { q.head = q.tail } else { @@ -40,7 +35,7 @@ func (q *queue) Enqueue(item Item) { q.size++ } -func (q *queue) Dequeue() Item { +func (q *queue[T]) Dequeue() T { first := q.head q.head = q.head.next if q.IsEmpty() { @@ -50,10 +45,10 @@ func (q *queue) Dequeue() Item { return first.item } -func (q *queue) Size() int { +func (q *queue[T]) Size() int { return q.size } -func (q *queue) IsEmpty() bool { +func (q *queue[T]) IsEmpty() bool { return q.head == nil } diff --git a/fundamentals/queue/queue_test.go b/fundamentals/queue/queue_test.go index 32e0c20..848bd66 100644 --- a/fundamentals/queue/queue_test.go +++ b/fundamentals/queue/queue_test.go @@ -6,13 +6,13 @@ import ( ) func TestSimple(t *testing.T) { - queue := NewQueue() + queue := NewQueue[int]() queue.Enqueue(10) queue.Enqueue(20) queue.Enqueue(30) - first, second := queue.Dequeue().(int), queue.Dequeue().(int) + first, second := queue.Dequeue(), queue.Dequeue() if first != 10 && second != 20 { log.Fatal("wrong order") @@ -20,7 +20,7 @@ func TestSimple(t *testing.T) { } func TestSize(t *testing.T) { - queue := NewQueue() + queue := NewQueue[int]() if queue.Size() != 0 { log.Fatal("empty queue should have size 0") diff --git a/go.mod b/go.mod index 44584f2..db7c2c3 100644 --- a/go.mod +++ b/go.mod @@ -1,3 +1,3 @@ module github.com/fotonmoton/algorithms -go 1.16 +go 1.18