Commit Diff


commit - 96a00272db52605790b2a6eadb899e5b04eb6a07
commit + 6ef75cdc94e38c534fcc0fa88719ee44459c2045
blob - d8acf70df24fb3798c293ffe0eb09b64f9563e9f
blob + 60489baac0595cb750096dd7d6993f138c6afafe
--- stack.go
+++ stack.go
@@ -23,8 +23,19 @@ func (s *Stack[T]) Size() int {
 	return s.size
 }
 
-func (s *Stack[T]) Pop() (*T, error) {
+func (s *Stack[T]) Pop() (T, error) {
 	if s.size == 0 {
+		var t T
+		return t, fmt.Errorf("tried to pop empty stack")
+	}
+	t := s.arr[s.size-1]
+	s.arr = s.arr[:s.size-1]
+	s.size--
+	return t, nil
+}
+
+func (s *Stack[T]) PopPtr() (*T, error) {
+	if s.size == 0 {
 		return nil, fmt.Errorf("tried to pop empty stack")
 	}
 	t := s.arr[s.size-1]
@@ -38,11 +49,18 @@ func (s *Stack[T]) Push(t T) {
 	s.size++
 }
 
-func (s *Stack[T]) Peek() T {
+func (s *Stack[T]) Peek() (T, error) {
+	if s.size == 0 {
+		var t T
+		return t, fmt.Errorf("tried to peek empty stack")
+	}
 	t := s.arr[s.size-1]
-	return t
+	return t, nil
 }
 
-func (s *Stack[T]) PeekPtr() *T {
-	return &(s.arr[s.size-1])
+func (s *Stack[T]) PeekPtr() (*T, error) {
+	if s.size == 0 {
+		return nil, fmt.Errorf("tried to peek empty stack")
+	}
+	return &(s.arr[s.size-1]), nil
 }
blob - b8b91a85ec1ca6b1ee51d5b241355c56ccc4f44c
blob + eda341468e95d85009cc71cb5d0c9ca299840b50
--- stack_test.go
+++ stack_test.go
@@ -15,8 +15,14 @@ func TestStackPush(t *testing.T) {
 	s.Push(2)
 	s.Push(10)
 
-	assert.Equal(t, s.Peek(), 10)
-	assert.Equal(t, *s.PeekPtr(), 10)
+	p, err := s.Peek()
+	assert.Equal(t, p, 10)
+	assert.NoError(t, err)
+
+	pp, err := s.PeekPtr()
+	assert.NotNil(t, pp)
+	assert.NoError(t, err)
+	assert.Equal(t, *pp, 10)
 }
 
 func TestStackPop(t *testing.T) {
@@ -25,15 +31,26 @@ func TestStackPop(t *testing.T) {
 	s.Push(10)
 
 	x, err := s.Pop()
-	assert.NotNil(t, x)
 	assert.NoError(t, err)
-	assert.Equal(t, *x, 10)
+	assert.Equal(t, x, 10)
+
+	y, err := s.PopPtr()
+	assert.NotNil(t, y)
+	assert.NoError(t, err)
+	assert.Equal(t, *y, 2)
 }
 
 func TestStackPopEmpty(t *testing.T) {
 	s := NewStack[int]()
 	x, err := s.Pop()
 	assert.Error(t, err)
+	assert.Zero(t, x)
+}
+
+func TestStackPopPtrEmpty(t *testing.T) {
+	s := NewStack[int]()
+	x, err := s.PopPtr()
+	assert.Error(t, err)
 	assert.Nil(t, x)
 }
 
@@ -53,17 +70,22 @@ func TestStackComplete(t *testing.T) {
 	s.Push(3)
 
 	assert.Equal(t, s.Size(), 3)
-	x := s.Peek()
+	x, err := s.Peek()
+	assert.NoError(t, err)
 	assert.Equal(t, 3, x)
 
-	y := s.PeekPtr()
+	y, err := s.PeekPtr()
 	assert.NotNil(t, y)
+	assert.NoError(t, err)
 	assert.Equal(t, 3, *y)
 
 	z, err := s.Pop()
 	assert.NoError(t, err)
-	assert.Equal(t, *z, 3)
-	assert.Equal(t, s.Peek(), 2)
+	assert.Equal(t, z, 3)
+
+	p, err := s.Peek()
+	assert.NoError(t, err)
+	assert.Equal(t, p, 2)
 	assert.Equal(t, s.Size(), 2)
 
 	s.Clear()