Skip to content

Commit

Permalink
test: super.BitSet 完善测试用例
Browse files Browse the repository at this point in the history
  • Loading branch information
kercylan98 committed Jan 22, 2024
1 parent 959abff commit f08f068
Show file tree
Hide file tree
Showing 3 changed files with 194 additions and 18 deletions.
13 changes: 13 additions & 0 deletions utils/super/bit_set.go
Original file line number Diff line number Diff line change
Expand Up @@ -7,9 +7,13 @@ import (
)

// NewBitSet 通过指定的 Bit 位创建一个 BitSet
// - 当指定的 Bit 位存在负数时,将会 panic
func NewBitSet[Bit generic.Integer](bits ...Bit) *BitSet[Bit] {
set := &BitSet[Bit]{set: make([]uint64, 0, 1)}
for _, bit := range bits {
if bit < 0 {
panic(fmt.Errorf("bit %v is negative", bit))
}
set.Set(bit)
}
return set
Expand Down Expand Up @@ -43,6 +47,15 @@ func (slf *BitSet[Bit]) Del(bit Bit) *BitSet[Bit] {
// Shrink 将 BitSet 中的比特位集合缩小到最小
// - 正常情况下当 BitSet 中的比特位超出 64 位时,将自动增长,当 BitSet 中的比特位数量减少时,可以使用该方法将 BitSet 中的比特位集合缩小到最小
func (slf *BitSet[Bit]) Shrink() *BitSet[Bit] {
switch len(slf.set) {
case 0:
return slf
case 1:
if slf.set[0] == 0 {
slf.set = nil
return slf
}
}
index := len(slf.set) - 1
if slf.set[index] != 0 {
return slf
Expand Down
74 changes: 74 additions & 0 deletions utils/super/bit_set_example_test.go
Original file line number Diff line number Diff line change
@@ -0,0 +1,74 @@
package super_test

import (
"fmt"
"github.com/kercylan98/minotaur/utils/super"
)

func ExampleNewBitSet() {
var bs = super.NewBitSet(1, 2, 3, 4, 5, 6, 7, 8, 9)
bs.Set(10)
fmt.Println(bs.Bits())
// Output:
// [1 2 3 4 5 6 7 8 9 10]
}

func ExampleBitSet_Set() {
var bs = super.NewBitSet[int]()
bs.Set(10)
fmt.Println(bs.Bits())
// Output:
// [10]
}

func ExampleBitSet_Del() {
var bs = super.NewBitSet(1, 2, 3, 4, 5, 6, 7, 8, 9)
bs.Del(1)
fmt.Println(bs.Bits())
// Output:
// [2 3 4 5 6 7 8 9]
}

func ExampleBitSet_Shrink() {
var bs = super.NewBitSet(111, 222, 333, 444)
fmt.Println(bs.Cap())
bs.Del(444)
fmt.Println(bs.Cap())
bs.Shrink()
fmt.Println(bs.Cap())
// Output:
// 448
// 448
// 384
}

func ExampleBitSet_Cap() {
var bs = super.NewBitSet(63)
fmt.Println(bs.Cap())
// Output:
// 64
}

func ExampleBitSet_Has() {
var bs = super.NewBitSet(1, 2, 3, 4, 5, 6, 7, 8, 9)
fmt.Println(bs.Has(1))
fmt.Println(bs.Has(10))
// Output:
// true
// false
}

func ExampleBitSet_Clear() {
var bs = super.NewBitSet(1, 2, 3, 4, 5, 6, 7, 8, 9)
bs.Clear()
fmt.Println(bs.Bits())
// Output:
// []
}

func ExampleBitSet_Len() {
var bs = super.NewBitSet(1, 2, 3, 4, 5, 6, 7, 8, 9)
fmt.Println(bs.Len())
// Output:
// 9
}
125 changes: 107 additions & 18 deletions utils/super/bit_set_test.go
Original file line number Diff line number Diff line change
Expand Up @@ -5,29 +5,118 @@ import (
"testing"
)

func TestNewBitSet(t *testing.T) {
var cases = []struct {
name string
in []int
shouldPanic bool
}{
{name: "normal", in: []int{1, 2, 3, 4, 5, 6, 7, 8, 9}},
{name: "empty", in: make([]int, 0)},
{name: "nil", in: nil},
{name: "negative", in: []int{-1, -2}, shouldPanic: true},
}

for _, c := range cases {
t.Run(c.name, func(t *testing.T) {
defer func() {
if r := recover(); r != nil && !c.shouldPanic {
t.Fatalf("panic: %v", r)
}
}()
bs := super.NewBitSet(c.in...)
t.Log(bs)
})
}
}

func TestBitSet_Set(t *testing.T) {
bs := super.NewBitSet(1, 2, 3, 4, 5, 6, 7, 8, 9, 10)
bs.Set(11)
bs.Set(12)
bs.Set(13)
t.Log(bs)
var cases = []struct {
name string
in []int
shouldPanic bool
}{
{name: "normal", in: []int{1, 2, 3, 4, 5, 6, 7, 8, 9}},
{name: "empty", in: make([]int, 0)},
{name: "nil", in: nil},
{name: "negative", in: []int{-1, -2}, shouldPanic: true},
}

for _, c := range cases {
t.Run(c.name, func(t *testing.T) {
defer func() {
if r := recover(); r != nil && !c.shouldPanic {
t.Fatalf("panic: %v", r)
}
}()
bs := super.NewBitSet[int]()
for _, bit := range c.in {
bs.Set(bit)
}
for _, bit := range c.in {
if !bs.Has(bit) {
t.Fatalf("bit %v not set", bit)
}
}
})
}
}

func TestBitSet_Del(t *testing.T) {
bs := super.NewBitSet(1, 2, 3, 4, 5, 6, 7, 8, 9, 10)
bs.Del(11)
bs.Del(12)
bs.Del(13)
bs.Del(10)
t.Log(bs)
var cases = []struct {
name string
in []int
shouldPanic bool
}{
{name: "normal", in: []int{1, 2, 3, 4, 5, 6, 7, 8, 9}},
{name: "empty", in: make([]int, 0)},
{name: "nil", in: nil},
{name: "negative", in: []int{-1, -2}, shouldPanic: true},
}

for _, c := range cases {
t.Run(c.name, func(t *testing.T) {
defer func() {
if r := recover(); r != nil && !c.shouldPanic {
t.Fatalf("panic: %v", r)
}
}()
bs := super.NewBitSet[int]()
for _, bit := range c.in {
bs.Set(bit)
}
for _, bit := range c.in {
bs.Del(bit)
}
for _, bit := range c.in {
if bs.Has(bit) {
t.Fatalf("bit %v not del", bit)
}
}
})
}
}

func TestBitSet_Shrink(t *testing.T) {
bs := super.NewBitSet(63)
t.Log(bs.Cap())
bs.Set(200)
t.Log(bs.Cap())
bs.Del(200)
bs.Shrink()
t.Log(bs.Cap())
var cases = []struct {
name string
in []int
}{
{name: "normal", in: []int{1, 2, 3, 4, 5, 6, 7, 8, 9}},
{name: "empty", in: make([]int, 0)},
{name: "nil", in: nil},
}

for _, c := range cases {
t.Run(c.name, func(t *testing.T) {
bs := super.NewBitSet(c.in...)
for _, v := range c.in {
bs.Del(v)
}
bs.Shrink()
if bs.Cap() != 0 {
t.Fatalf("cap %v != 0", bs.Cap())
}
})
}
}

0 comments on commit f08f068

Please sign in to comment.