diff --git a/benchmark_test.go b/benchmark_test.go deleted file mode 100644 index 97b7389e..00000000 --- a/benchmark_test.go +++ /dev/null @@ -1,62 +0,0 @@ -package lo - -import ( - "math/rand" - "strconv" - "testing" - "time" - - lop "github.com/samber/lo/parallel" - "github.com/thoas/go-funk" -) - -func sliceGenerator(size uint) []int64 { - r := rand.New(rand.NewSource(time.Now().Unix())) - - result := make([]int64, size) - - for i := uint(0); i < size; i++ { - result[i] = r.Int63() - } - - return result -} - -func BenchmarkMap(b *testing.B) { - arr := sliceGenerator(1000000) - - b.Run("lo.Map", func(b *testing.B) { - for n := 0; n < b.N; n++ { - _ = Map(arr, func(x int64, i int) string { - return strconv.FormatInt(x, 10) - }) - } - }) - - b.Run("lop.Map", func(b *testing.B) { - for n := 0; n < b.N; n++ { - _ = lop.Map(arr, func(x int64, i int) string { - return strconv.FormatInt(x, 10) - }) - } - }) - - b.Run("reflect", func(b *testing.B) { - for n := 0; n < b.N; n++ { - _ = funk.Map(arr, func(x int64) string { - return strconv.FormatInt(x, 10) - }) - } - }) - - b.Run("for", func(b *testing.B) { - for n := 0; n < b.N; n++ { - results := make([]string, len(arr)) - - for i, item := range arr { - result := strconv.FormatInt(item, 10) - results[i] = result - } - } - }) -} diff --git a/channel_test.go b/channel_test.go deleted file mode 100644 index 04c87164..00000000 --- a/channel_test.go +++ /dev/null @@ -1,390 +0,0 @@ -package lo - -import ( - "math/rand" - "testing" - "time" - - "github.com/stretchr/testify/assert" -) - -func TestChannelDispatcher(t *testing.T) { - t.Parallel() - testWithTimeout(t, 100*time.Millisecond) - is := assert.New(t) - - ch := make(chan int, 10) - - ch <- 0 - ch <- 1 - ch <- 2 - ch <- 3 - - is.Equal(4, len(ch)) - - children := ChannelDispatcher(ch, 5, 10, DispatchingStrategyRoundRobin[int]) - time.Sleep(10 * time.Millisecond) - - // check channels allocation - is.Equal(5, len(children)) - - is.Equal(10, cap(children[0])) - is.Equal(10, cap(children[1])) - is.Equal(10, cap(children[2])) - is.Equal(10, cap(children[3])) - is.Equal(10, cap(children[4])) - - is.Equal(1, len(children[0])) - is.Equal(1, len(children[1])) - is.Equal(1, len(children[2])) - is.Equal(1, len(children[3])) - is.Equal(0, len(children[4])) - - // check channels content - is.Equal(0, len(ch)) - - msg0, ok0 := <-children[0] - is.Equal(ok0, true) - is.Equal(msg0, 0) - - msg1, ok1 := <-children[1] - is.Equal(ok1, true) - is.Equal(msg1, 1) - - msg2, ok2 := <-children[2] - is.Equal(ok2, true) - is.Equal(msg2, 2) - - msg3, ok3 := <-children[3] - is.Equal(ok3, true) - is.Equal(msg3, 3) - - // msg4, ok4 := <-children[4] - // is.Equal(ok4, false) - // is.Equal(msg4, 0) - // is.Nil(children[4]) - - // check it is closed - close(ch) - time.Sleep(10 * time.Millisecond) - is.Panics(func() { - ch <- 42 - }) - - msg0, ok0 = <-children[0] - is.Equal(ok0, false) - is.Equal(msg0, 0) - - msg1, ok1 = <-children[1] - is.Equal(ok1, false) - is.Equal(msg1, 0) - - msg2, ok2 = <-children[2] - is.Equal(ok2, false) - is.Equal(msg2, 0) - - msg3, ok3 = <-children[3] - is.Equal(ok3, false) - is.Equal(msg3, 0) - - msg4, ok4 := <-children[4] - is.Equal(ok4, false) - is.Equal(msg4, 0) - - // unbuffered channels - children = ChannelDispatcher(ch, 5, 0, DispatchingStrategyRoundRobin[int]) - is.Equal(0, cap(children[0])) -} - -func TestDispatchingStrategyRoundRobin(t *testing.T) { - t.Parallel() - testWithTimeout(t, 10*time.Millisecond) - is := assert.New(t) - - children := createChannels[int](3, 2) - rochildren := channelsToReadOnly(children) - defer closeChannels(children) - - is.Equal(0, DispatchingStrategyRoundRobin(42, 0, rochildren)) - is.Equal(1, DispatchingStrategyRoundRobin(42, 1, rochildren)) - is.Equal(2, DispatchingStrategyRoundRobin(42, 2, rochildren)) - is.Equal(0, DispatchingStrategyRoundRobin(42, 3, rochildren)) -} - -func TestDispatchingStrategyRandom(t *testing.T) { - testWithTimeout(t, 10*time.Millisecond) - is := assert.New(t) - - // with this seed, the order of random channels are: 1 - 0 - rand.Seed(14) - - children := createChannels[int](2, 2) - rochildren := channelsToReadOnly(children) - defer closeChannels(children) - - for i := 0; i < 2; i++ { - children[1] <- i - } - - is.Equal(0, DispatchingStrategyRandom(42, 0, rochildren)) -} - -func TestDispatchingStrategyWeightedRandom(t *testing.T) { - t.Parallel() - testWithTimeout(t, 10*time.Millisecond) - is := assert.New(t) - - children := createChannels[int](2, 2) - rochildren := channelsToReadOnly(children) - defer closeChannels(children) - - dispatcher := DispatchingStrategyWeightedRandom[int]([]int{0, 42}) - - is.Equal(1, dispatcher(42, 0, rochildren)) - children[0] <- 0 - is.Equal(1, dispatcher(42, 0, rochildren)) - children[1] <- 1 - is.Equal(1, dispatcher(42, 0, rochildren)) -} - -func TestDispatchingStrategyFirst(t *testing.T) { - t.Parallel() - testWithTimeout(t, 10*time.Millisecond) - is := assert.New(t) - - children := createChannels[int](2, 2) - rochildren := channelsToReadOnly(children) - defer closeChannels(children) - - is.Equal(0, DispatchingStrategyFirst(42, 0, rochildren)) - children[0] <- 0 - is.Equal(0, DispatchingStrategyFirst(42, 0, rochildren)) - children[0] <- 1 - is.Equal(1, DispatchingStrategyFirst(42, 0, rochildren)) -} - -func TestDispatchingStrategyLeast(t *testing.T) { - t.Parallel() - testWithTimeout(t, 10*time.Millisecond) - is := assert.New(t) - - children := createChannels[int](2, 2) - rochildren := channelsToReadOnly(children) - defer closeChannels(children) - - is.Equal(0, DispatchingStrategyLeast(42, 0, rochildren)) - children[0] <- 0 - is.Equal(1, DispatchingStrategyLeast(42, 0, rochildren)) - children[1] <- 0 - is.Equal(0, DispatchingStrategyLeast(42, 0, rochildren)) - children[0] <- 1 - is.Equal(1, DispatchingStrategyLeast(42, 0, rochildren)) - children[1] <- 1 - is.Equal(0, DispatchingStrategyLeast(42, 0, rochildren)) -} - -func TestDispatchingStrategyMost(t *testing.T) { - t.Parallel() - testWithTimeout(t, 10*time.Millisecond) - is := assert.New(t) - - children := createChannels[int](2, 2) - rochildren := channelsToReadOnly(children) - defer closeChannels(children) - - is.Equal(0, DispatchingStrategyMost(42, 0, rochildren)) - children[0] <- 0 - is.Equal(0, DispatchingStrategyMost(42, 0, rochildren)) - children[1] <- 0 - is.Equal(0, DispatchingStrategyMost(42, 0, rochildren)) - children[0] <- 1 - is.Equal(0, DispatchingStrategyMost(42, 0, rochildren)) - children[1] <- 1 - is.Equal(0, DispatchingStrategyMost(42, 0, rochildren)) -} - -func TestSliceToChannel(t *testing.T) { - t.Parallel() - testWithTimeout(t, 10*time.Millisecond) - is := assert.New(t) - - ch := SliceToChannel(2, []int{1, 2, 3}) - - r1, ok1 := <-ch - r2, ok2 := <-ch - r3, ok3 := <-ch - is.True(ok1) - is.Equal(1, r1) - is.True(ok2) - is.Equal(2, r2) - is.True(ok3) - is.Equal(3, r3) - - _, ok4 := <-ch - is.False(ok4) -} - -func TestChannelToSlice(t *testing.T) { - t.Parallel() - testWithTimeout(t, 10*time.Millisecond) - is := assert.New(t) - - ch := SliceToChannel(2, []int{1, 2, 3}) - items := ChannelToSlice(ch) - - is.Equal([]int{1, 2, 3}, items) -} - -func TestGenerate(t *testing.T) { - t.Parallel() - testWithTimeout(t, 10*time.Millisecond) - is := assert.New(t) - - generator := func(yield func(int)) { - yield(0) - yield(1) - yield(2) - yield(3) - } - - i := 0 - - for v := range Generator(2, generator) { - is.Equal(i, v) - i++ - } - - is.Equal(i, 4) -} - -func TestBuffer(t *testing.T) { - t.Parallel() - testWithTimeout(t, 10*time.Millisecond) - is := assert.New(t) - - ch := SliceToChannel(2, []int{1, 2, 3}) - - items1, length1, _, ok1 := Buffer(ch, 2) - items2, length2, _, ok2 := Buffer(ch, 2) - items3, length3, _, ok3 := Buffer(ch, 2) - - is.Equal([]int{1, 2}, items1) - is.Equal(2, length1) - is.True(ok1) - is.Equal([]int{3}, items2) - is.Equal(1, length2) - is.False(ok2) - is.Equal([]int{}, items3) - is.Equal(0, length3) - is.False(ok3) -} - -func TestBufferWithTimeout(t *testing.T) { - t.Parallel() - testWithTimeout(t, 200*time.Millisecond) - is := assert.New(t) - - generator := func(yield func(int)) { - for i := 0; i < 5; i++ { - yield(i) - time.Sleep(10 * time.Millisecond) - } - } - ch := Generator(0, generator) - - items1, length1, _, ok1 := BufferWithTimeout(ch, 20, 15*time.Millisecond) - is.Equal([]int{0, 1}, items1) - is.Equal(2, length1) - is.True(ok1) - - items2, length2, _, ok2 := BufferWithTimeout(ch, 20, 2*time.Millisecond) - is.Equal([]int{}, items2) - is.Equal(0, length2) - is.True(ok2) - - items3, length3, _, ok3 := BufferWithTimeout(ch, 1, 30*time.Millisecond) - is.Equal([]int{2}, items3) - is.Equal(1, length3) - is.True(ok3) - - items4, length4, _, ok4 := BufferWithTimeout(ch, 2, 25*time.Millisecond) - is.Equal([]int{3, 4}, items4) - is.Equal(2, length4) - is.True(ok4) - - items5, length5, _, ok5 := BufferWithTimeout(ch, 3, 25*time.Millisecond) - is.Equal([]int{}, items5) - is.Equal(0, length5) - is.False(ok5) -} - -func TestFanIn(t *testing.T) { - t.Parallel() - testWithTimeout(t, 100*time.Millisecond) - is := assert.New(t) - - upstreams := createChannels[int](3, 10) - roupstreams := channelsToReadOnly(upstreams) - for i := range roupstreams { - go func(i int) { - upstreams[i] <- 1 - upstreams[i] <- 1 - close(upstreams[i]) - }(i) - } - out := FanIn(10, roupstreams...) - time.Sleep(10 * time.Millisecond) - - // check input channels - is.Equal(0, len(roupstreams[0])) - is.Equal(0, len(roupstreams[1])) - is.Equal(0, len(roupstreams[2])) - - // check channels allocation - is.Equal(6, len(out)) - is.Equal(10, cap(out)) - - // check channels content - for i := 0; i < 6; i++ { - msg0, ok0 := <-out - is.Equal(true, ok0) - is.Equal(1, msg0) - } - - // check it is closed - time.Sleep(10 * time.Millisecond) - msg0, ok0 := <-out - is.Equal(false, ok0) - is.Equal(0, msg0) -} - -func TestFanOut(t *testing.T) { - t.Parallel() - testWithTimeout(t, 100*time.Millisecond) - is := assert.New(t) - - upstream := SliceToChannel(10, []int{0, 1, 2, 3, 4, 5}) - rodownstreams := FanOut(3, 10, upstream) - - time.Sleep(10 * time.Millisecond) - - // check output channels - is.Equal(3, len(rodownstreams)) - - // check channels allocation - for i := range rodownstreams { - is.Equal(6, len(rodownstreams[i])) - is.Equal(10, cap(rodownstreams[i])) - is.Equal([]int{0, 1, 2, 3, 4, 5}, ChannelToSlice(rodownstreams[i])) - } - - // check it is closed - time.Sleep(10 * time.Millisecond) - - // check channels allocation - for i := range rodownstreams { - msg, ok := <-rodownstreams[i] - is.Equal(false, ok) - is.Equal(0, msg) - } -} diff --git a/concurrency_test.go b/concurrency_test.go deleted file mode 100644 index ae65efdd..00000000 --- a/concurrency_test.go +++ /dev/null @@ -1,214 +0,0 @@ -package lo - -import ( - "sync" - "testing" - "time" - - "github.com/stretchr/testify/assert" -) - -func TestSynchronize(t *testing.T) { - t.Parallel() - testWithTimeout(t, 100*time.Millisecond) - is := assert.New(t) - - // check that callbacks are not executed concurrently - { - start := time.Now() - - wg := sync.WaitGroup{} - wg.Add(10) - - s := Synchronize() - - for i := 0; i < 10; i++ { - go s.Do(func() { - time.Sleep(5 * time.Millisecond) - wg.Done() - }) - } - - wg.Wait() - - duration := time.Since(start) - - is.Greater(duration, 50*time.Millisecond) - is.Less(duration, 60*time.Millisecond) - } - - // check locker is locked - { - mu := &sync.Mutex{} - s := Synchronize(mu) - - s.Do(func() { - is.False(mu.TryLock()) - }) - is.True(mu.TryLock()) - - Try0(func() { - mu.Unlock() - }) - } - - // check we don't accept multiple arguments - { - is.PanicsWithValue("unexpected arguments", func() { - mu := &sync.Mutex{} - Synchronize(mu, mu, mu) - }) - } -} - -func TestAsync(t *testing.T) { - t.Parallel() - testWithTimeout(t, 100*time.Millisecond) - is := assert.New(t) - - sync := make(chan struct{}) - - ch := Async(func() int { - <-sync - return 10 - }) - - sync <- struct{}{} - - select { - case result := <-ch: - is.Equal(result, 10) - case <-time.After(time.Millisecond): - is.Fail("Async should not block") - } -} - -func TestAsyncX(t *testing.T) { - t.Parallel() - testWithTimeout(t, 100*time.Millisecond) - is := assert.New(t) - - { - sync := make(chan struct{}) - - ch := Async0(func() { - <-sync - }) - - sync <- struct{}{} - - select { - case <-ch: - case <-time.After(time.Millisecond): - is.Fail("Async0 should not block") - } - } - - { - sync := make(chan struct{}) - - ch := Async1(func() int { - <-sync - return 10 - }) - - sync <- struct{}{} - - select { - case result := <-ch: - is.Equal(result, 10) - case <-time.After(time.Millisecond): - is.Fail("Async1 should not block") - } - } - - { - sync := make(chan struct{}) - - ch := Async2(func() (int, string) { - <-sync - return 10, "Hello" - }) - - sync <- struct{}{} - - select { - case result := <-ch: - is.Equal(result, Tuple2[int, string]{10, "Hello"}) - case <-time.After(time.Millisecond): - is.Fail("Async2 should not block") - } - } - - { - sync := make(chan struct{}) - - ch := Async3(func() (int, string, bool) { - <-sync - return 10, "Hello", true - }) - - sync <- struct{}{} - - select { - case result := <-ch: - is.Equal(result, Tuple3[int, string, bool]{10, "Hello", true}) - case <-time.After(time.Millisecond): - is.Fail("Async3 should not block") - } - } - - { - sync := make(chan struct{}) - - ch := Async4(func() (int, string, bool, float64) { - <-sync - return 10, "Hello", true, 3.14 - }) - - sync <- struct{}{} - - select { - case result := <-ch: - is.Equal(result, Tuple4[int, string, bool, float64]{10, "Hello", true, 3.14}) - case <-time.After(time.Millisecond): - is.Fail("Async4 should not block") - } - } - - { - sync := make(chan struct{}) - - ch := Async5(func() (int, string, bool, float64, string) { - <-sync - return 10, "Hello", true, 3.14, "World" - }) - - sync <- struct{}{} - - select { - case result := <-ch: - is.Equal(result, Tuple5[int, string, bool, float64, string]{10, "Hello", true, 3.14, "World"}) - case <-time.After(time.Millisecond): - is.Fail("Async5 should not block") - } - } - - { - sync := make(chan struct{}) - - ch := Async6(func() (int, string, bool, float64, string, int) { - <-sync - return 10, "Hello", true, 3.14, "World", 100 - }) - - sync <- struct{}{} - - select { - case result := <-ch: - is.Equal(result, Tuple6[int, string, bool, float64, string, int]{10, "Hello", true, 3.14, "World", 100}) - case <-time.After(time.Millisecond): - is.Fail("Async6 should not block") - } - } -} diff --git a/condition_example_test.go b/condition_example_test.go deleted file mode 100644 index 1700967e..00000000 --- a/condition_example_test.go +++ /dev/null @@ -1,489 +0,0 @@ -package lo - -import ( - "fmt" -) - -func ExampleTernary() { - result := Ternary(true, "a", "b") - - fmt.Printf("%v", result) - // Output: a -} - -func ExampleTernaryF() { - result := TernaryF(true, func() string { return "a" }, func() string { return "b" }) - - fmt.Printf("%v", result) - // Output: a -} - -func ExampleIf() { - result1 := If(true, 1). - ElseIf(false, 2). - Else(3) - - result2 := If(false, 1). - ElseIf(true, 2). - Else(3) - - result3 := If(false, 1). - ElseIf(false, 2). - Else(3) - - result4 := IfF(true, func() int { return 1 }). - ElseIfF(false, func() int { return 2 }). - ElseF(func() int { return 3 }) - - result5 := IfF(false, func() int { return 1 }). - ElseIfF(true, func() int { return 2 }). - ElseF(func() int { return 3 }) - - result6 := IfF(false, func() int { return 1 }). - ElseIfF(false, func() int { return 2 }). - ElseF(func() int { return 3 }) - - fmt.Printf("%v\n", result1) - fmt.Printf("%v\n", result2) - fmt.Printf("%v\n", result3) - fmt.Printf("%v\n", result4) - fmt.Printf("%v\n", result5) - fmt.Printf("%v\n", result6) - // Output: - // 1 - // 2 - // 3 - // 1 - // 2 - // 3 -} - -func ExampleIfF() { - result1 := If(true, 1). - ElseIf(false, 2). - Else(3) - - result2 := If(false, 1). - ElseIf(true, 2). - Else(3) - - result3 := If(false, 1). - ElseIf(false, 2). - Else(3) - - result4 := IfF(true, func() int { return 1 }). - ElseIfF(false, func() int { return 2 }). - ElseF(func() int { return 3 }) - - result5 := IfF(false, func() int { return 1 }). - ElseIfF(true, func() int { return 2 }). - ElseF(func() int { return 3 }) - - result6 := IfF(false, func() int { return 1 }). - ElseIfF(false, func() int { return 2 }). - ElseF(func() int { return 3 }) - - fmt.Printf("%v\n", result1) - fmt.Printf("%v\n", result2) - fmt.Printf("%v\n", result3) - fmt.Printf("%v\n", result4) - fmt.Printf("%v\n", result5) - fmt.Printf("%v\n", result6) - // Output: - // 1 - // 2 - // 3 - // 1 - // 2 - // 3 -} - -func ExampleifElse_ElseIf() { - result1 := If(true, 1). - ElseIf(false, 2). - Else(3) - - result2 := If(false, 1). - ElseIf(true, 2). - Else(3) - - result3 := If(false, 1). - ElseIf(false, 2). - Else(3) - - result4 := IfF(true, func() int { return 1 }). - ElseIfF(false, func() int { return 2 }). - ElseF(func() int { return 3 }) - - result5 := IfF(false, func() int { return 1 }). - ElseIfF(true, func() int { return 2 }). - ElseF(func() int { return 3 }) - - result6 := IfF(false, func() int { return 1 }). - ElseIfF(false, func() int { return 2 }). - ElseF(func() int { return 3 }) - - fmt.Printf("%v\n", result1) - fmt.Printf("%v\n", result2) - fmt.Printf("%v\n", result3) - fmt.Printf("%v\n", result4) - fmt.Printf("%v\n", result5) - fmt.Printf("%v\n", result6) - // Output: - // 1 - // 2 - // 3 - // 1 - // 2 - // 3 -} - -func ExampleifElse_ElseIfF() { - result1 := If(true, 1). - ElseIf(false, 2). - Else(3) - - result2 := If(false, 1). - ElseIf(true, 2). - Else(3) - - result3 := If(false, 1). - ElseIf(false, 2). - Else(3) - - result4 := IfF(true, func() int { return 1 }). - ElseIfF(false, func() int { return 2 }). - ElseF(func() int { return 3 }) - - result5 := IfF(false, func() int { return 1 }). - ElseIfF(true, func() int { return 2 }). - ElseF(func() int { return 3 }) - - result6 := IfF(false, func() int { return 1 }). - ElseIfF(false, func() int { return 2 }). - ElseF(func() int { return 3 }) - - fmt.Printf("%v\n", result1) - fmt.Printf("%v\n", result2) - fmt.Printf("%v\n", result3) - fmt.Printf("%v\n", result4) - fmt.Printf("%v\n", result5) - fmt.Printf("%v\n", result6) - // Output: - // 1 - // 2 - // 3 - // 1 - // 2 - // 3 -} - -func ExampleifElse_Else() { - result1 := If(true, 1). - ElseIf(false, 2). - Else(3) - - result2 := If(false, 1). - ElseIf(true, 2). - Else(3) - - result3 := If(false, 1). - ElseIf(false, 2). - Else(3) - - result4 := IfF(true, func() int { return 1 }). - ElseIfF(false, func() int { return 2 }). - ElseF(func() int { return 3 }) - - result5 := IfF(false, func() int { return 1 }). - ElseIfF(true, func() int { return 2 }). - ElseF(func() int { return 3 }) - - result6 := IfF(false, func() int { return 1 }). - ElseIfF(false, func() int { return 2 }). - ElseF(func() int { return 3 }) - - fmt.Printf("%v\n", result1) - fmt.Printf("%v\n", result2) - fmt.Printf("%v\n", result3) - fmt.Printf("%v\n", result4) - fmt.Printf("%v\n", result5) - fmt.Printf("%v\n", result6) - // Output: - // 1 - // 2 - // 3 - // 1 - // 2 - // 3 -} - -func ExampleifElse_ElseF() { - result1 := If(true, 1). - ElseIf(false, 2). - Else(3) - - result2 := If(false, 1). - ElseIf(true, 2). - Else(3) - - result3 := If(false, 1). - ElseIf(false, 2). - Else(3) - - result4 := IfF(true, func() int { return 1 }). - ElseIfF(false, func() int { return 2 }). - ElseF(func() int { return 3 }) - - result5 := IfF(false, func() int { return 1 }). - ElseIfF(true, func() int { return 2 }). - ElseF(func() int { return 3 }) - - result6 := IfF(false, func() int { return 1 }). - ElseIfF(false, func() int { return 2 }). - ElseF(func() int { return 3 }) - - fmt.Printf("%v\n", result1) - fmt.Printf("%v\n", result2) - fmt.Printf("%v\n", result3) - fmt.Printf("%v\n", result4) - fmt.Printf("%v\n", result5) - fmt.Printf("%v\n", result6) - // Output: - // 1 - // 2 - // 3 - // 1 - // 2 - // 3 -} - -func ExampleSwitch() { - result1 := Switch[int, string](1). - Case(1, "1"). - Case(2, "2"). - Default("3") - - result2 := Switch[int, string](2). - Case(1, "1"). - Case(2, "2"). - Default("3") - - result3 := Switch[int, string](42). - Case(1, "1"). - Case(2, "2"). - Default("3") - - result4 := Switch[int, string](1). - CaseF(1, func() string { return "1" }). - CaseF(2, func() string { return "2" }). - DefaultF(func() string { return "3" }) - - result5 := Switch[int, string](2). - CaseF(1, func() string { return "1" }). - CaseF(2, func() string { return "2" }). - DefaultF(func() string { return "3" }) - - result6 := Switch[int, string](42). - CaseF(1, func() string { return "1" }). - CaseF(2, func() string { return "2" }). - DefaultF(func() string { return "3" }) - - fmt.Printf("%v\n", result1) - fmt.Printf("%v\n", result2) - fmt.Printf("%v\n", result3) - fmt.Printf("%v\n", result4) - fmt.Printf("%v\n", result5) - fmt.Printf("%v\n", result6) - // Output: - // 1 - // 2 - // 3 - // 1 - // 2 - // 3 -} - -func ExampleswitchCase_Case() { - result1 := Switch[int, string](1). - Case(1, "1"). - Case(2, "2"). - Default("3") - - result2 := Switch[int, string](2). - Case(1, "1"). - Case(2, "2"). - Default("3") - - result3 := Switch[int, string](42). - Case(1, "1"). - Case(2, "2"). - Default("3") - - result4 := Switch[int, string](1). - CaseF(1, func() string { return "1" }). - CaseF(2, func() string { return "2" }). - DefaultF(func() string { return "3" }) - - result5 := Switch[int, string](2). - CaseF(1, func() string { return "1" }). - CaseF(2, func() string { return "2" }). - DefaultF(func() string { return "3" }) - - result6 := Switch[int, string](42). - CaseF(1, func() string { return "1" }). - CaseF(2, func() string { return "2" }). - DefaultF(func() string { return "3" }) - - fmt.Printf("%v\n", result1) - fmt.Printf("%v\n", result2) - fmt.Printf("%v\n", result3) - fmt.Printf("%v\n", result4) - fmt.Printf("%v\n", result5) - fmt.Printf("%v\n", result6) - // Output: - // 1 - // 2 - // 3 - // 1 - // 2 - // 3 -} - -func ExampleswitchCase_CaseF() { - result1 := Switch[int, string](1). - Case(1, "1"). - Case(2, "2"). - Default("3") - - result2 := Switch[int, string](2). - Case(1, "1"). - Case(2, "2"). - Default("3") - - result3 := Switch[int, string](42). - Case(1, "1"). - Case(2, "2"). - Default("3") - - result4 := Switch[int, string](1). - CaseF(1, func() string { return "1" }). - CaseF(2, func() string { return "2" }). - DefaultF(func() string { return "3" }) - - result5 := Switch[int, string](2). - CaseF(1, func() string { return "1" }). - CaseF(2, func() string { return "2" }). - DefaultF(func() string { return "3" }) - - result6 := Switch[int, string](42). - CaseF(1, func() string { return "1" }). - CaseF(2, func() string { return "2" }). - DefaultF(func() string { return "3" }) - - fmt.Printf("%v\n", result1) - fmt.Printf("%v\n", result2) - fmt.Printf("%v\n", result3) - fmt.Printf("%v\n", result4) - fmt.Printf("%v\n", result5) - fmt.Printf("%v\n", result6) - // Output: - // 1 - // 2 - // 3 - // 1 - // 2 - // 3 -} - -func ExampleswitchCase_Default() { - result1 := Switch[int, string](1). - Case(1, "1"). - Case(2, "2"). - Default("3") - - result2 := Switch[int, string](2). - Case(1, "1"). - Case(2, "2"). - Default("3") - - result3 := Switch[int, string](42). - Case(1, "1"). - Case(2, "2"). - Default("3") - - result4 := Switch[int, string](1). - CaseF(1, func() string { return "1" }). - CaseF(2, func() string { return "2" }). - DefaultF(func() string { return "3" }) - - result5 := Switch[int, string](2). - CaseF(1, func() string { return "1" }). - CaseF(2, func() string { return "2" }). - DefaultF(func() string { return "3" }) - - result6 := Switch[int, string](42). - CaseF(1, func() string { return "1" }). - CaseF(2, func() string { return "2" }). - DefaultF(func() string { return "3" }) - - fmt.Printf("%v\n", result1) - fmt.Printf("%v\n", result2) - fmt.Printf("%v\n", result3) - fmt.Printf("%v\n", result4) - fmt.Printf("%v\n", result5) - fmt.Printf("%v\n", result6) - // Output: - // 1 - // 2 - // 3 - // 1 - // 2 - // 3 -} - -func ExampleswitchCase_DefaultF() { - result1 := Switch[int, string](1). - Case(1, "1"). - Case(2, "2"). - Default("3") - - result2 := Switch[int, string](2). - Case(1, "1"). - Case(2, "2"). - Default("3") - - result3 := Switch[int, string](42). - Case(1, "1"). - Case(2, "2"). - Default("3") - - result4 := Switch[int, string](1). - CaseF(1, func() string { return "1" }). - CaseF(2, func() string { return "2" }). - DefaultF(func() string { return "3" }) - - result5 := Switch[int, string](2). - CaseF(1, func() string { return "1" }). - CaseF(2, func() string { return "2" }). - DefaultF(func() string { return "3" }) - - result6 := Switch[int, string](42). - CaseF(1, func() string { return "1" }). - CaseF(2, func() string { return "2" }). - DefaultF(func() string { return "3" }) - - fmt.Printf("%v\n", result1) - fmt.Printf("%v\n", result2) - fmt.Printf("%v\n", result3) - fmt.Printf("%v\n", result4) - fmt.Printf("%v\n", result5) - fmt.Printf("%v\n", result6) - // Output: - // 1 - // 2 - // 3 - // 1 - // 2 - // 3 -} diff --git a/condition_test.go b/condition_test.go deleted file mode 100644 index ffb1e542..00000000 --- a/condition_test.go +++ /dev/null @@ -1,88 +0,0 @@ -package lo - -import ( - "testing" - - "github.com/stretchr/testify/assert" -) - -func TestTernary(t *testing.T) { - t.Parallel() - is := assert.New(t) - - result1 := Ternary(true, "a", "b") - result2 := Ternary(false, "a", "b") - - is.Equal(result1, "a") - is.Equal(result2, "b") -} - -func TestTernaryF(t *testing.T) { - is := assert.New(t) - - result1 := TernaryF(true, func() string { return "a" }, func() string { return "b" }) - result2 := TernaryF(false, func() string { return "a" }, func() string { return "b" }) - - is.Equal(result1, "a") - is.Equal(result2, "b") -} - -func TestIfElse(t *testing.T) { - t.Parallel() - is := assert.New(t) - - result1 := If(true, 1).ElseIf(false, 2).Else(3) - result2 := If(true, 1).ElseIf(true, 2).Else(3) - result3 := If(false, 1).ElseIf(true, 2).Else(3) - result4 := If(false, 1).ElseIf(false, 2).Else(3) - - is.Equal(result1, 1) - is.Equal(result2, 1) - is.Equal(result3, 2) - is.Equal(result4, 3) -} - -func TestIfFElseF(t *testing.T) { - t.Parallel() - is := assert.New(t) - - result1 := IfF(true, func() int { return 1 }).ElseIfF(false, func() int { return 2 }).ElseF(func() int { return 3 }) - result2 := IfF(true, func() int { return 1 }).ElseIfF(true, func() int { return 2 }).ElseF(func() int { return 3 }) - result3 := IfF(false, func() int { return 1 }).ElseIfF(true, func() int { return 2 }).ElseF(func() int { return 3 }) - result4 := IfF(false, func() int { return 1 }).ElseIfF(false, func() int { return 2 }).ElseF(func() int { return 3 }) - - is.Equal(result1, 1) - is.Equal(result2, 1) - is.Equal(result3, 2) - is.Equal(result4, 3) -} - -func TestSwitchCase(t *testing.T) { - t.Parallel() - is := assert.New(t) - - result1 := Switch[int, int](42).Case(42, 1).Case(1, 2).Default(3) - result2 := Switch[int, int](42).Case(42, 1).Case(42, 2).Default(3) - result3 := Switch[int, int](42).Case(1, 1).Case(42, 2).Default(3) - result4 := Switch[int, int](42).Case(1, 1).Case(1, 2).Default(3) - - is.Equal(result1, 1) - is.Equal(result2, 1) - is.Equal(result3, 2) - is.Equal(result4, 3) -} - -func TestSwitchCaseF(t *testing.T) { - t.Parallel() - is := assert.New(t) - - result1 := Switch[int, int](42).CaseF(42, func() int { return 1 }).CaseF(1, func() int { return 2 }).DefaultF(func() int { return 3 }) - result2 := Switch[int, int](42).CaseF(42, func() int { return 1 }).CaseF(42, func() int { return 2 }).DefaultF(func() int { return 3 }) - result3 := Switch[int, int](42).CaseF(1, func() int { return 1 }).CaseF(42, func() int { return 2 }).DefaultF(func() int { return 3 }) - result4 := Switch[int, int](42).CaseF(1, func() int { return 1 }).CaseF(1, func() int { return 2 }).DefaultF(func() int { return 3 }) - - is.Equal(result1, 1) - is.Equal(result2, 1) - is.Equal(result3, 2) - is.Equal(result4, 3) -} diff --git a/docker-compose.yml b/docker-compose.yml deleted file mode 100644 index 511e85fd..00000000 --- a/docker-compose.yml +++ /dev/null @@ -1,9 +0,0 @@ -version: '3' - -services: - dev: - image: golang:1.18-bullseye - volumes: - - ./:/go/src/github.com/samber/lo - working_dir: /go/src/github.com/samber/lo - command: make watch-test diff --git a/errors_example_test.go b/errors_example_test.go deleted file mode 100644 index 1594a0c2..00000000 --- a/errors_example_test.go +++ /dev/null @@ -1,429 +0,0 @@ -package lo - -import ( - "fmt" -) - -func ExampleValidate() { - i := 42 - - err1 := Validate(i < 0, "expected %d < 0", i) - err2 := Validate(i > 0, "expected %d > 0", i) - - fmt.Printf("%v\n%v", err1, err2) - // Output: - // expected 42 < 0 - // -} - -func ExampleMust() { - defer func() { - _ = recover() - }() - - // won't panic - Must(42, nil) - - // won't panic - cb := func() (int, error) { - return 42, nil - } - Must(cb()) - - // will panic - Must(42, fmt.Errorf("my error")) - - // will panic with error message - Must(42, fmt.Errorf("world"), "hello") -} - -func ExampleMust0() { - defer func() { - _ = recover() - }() - - // won't panic - Must0(nil) - - // will panic - Must0(fmt.Errorf("my error")) - - // will panic with error message - Must0(fmt.Errorf("world"), "hello") -} - -func ExampleMust1() { - defer func() { - _ = recover() - }() - - // won't panic - Must1(42, nil) - - // won't panic - cb := func() (int, error) { - return 42, nil - } - Must1(cb()) - - // will panic - Must1(42, fmt.Errorf("my error")) - - // will panic with error message - Must1(42, fmt.Errorf("world"), "hello") -} - -func ExampleMust2() { - defer func() { - _ = recover() - }() - - // won't panic - Must2(42, "hello", nil) - - // will panic - Must2(42, "hello", fmt.Errorf("my error")) - - // will panic with error message - Must2(42, "hello", fmt.Errorf("world"), "hello") -} - -func ExampleMust3() { - defer func() { - _ = recover() - }() - - // won't panic - Must3(42, "hello", 4.2, nil) - - // will panic - Must3(42, "hello", 4.2, fmt.Errorf("my error")) - - // will panic with error message - Must3(42, "hello", 4.2, fmt.Errorf("world"), "hello") -} - -func ExampleMust4() { - defer func() { - _ = recover() - }() - - // won't panic - Must4(42, "hello", 4.2, true, nil) - - // will panic - Must4(42, "hello", 4.2, true, fmt.Errorf("my error")) - - // will panic with error message - Must4(42, "hello", 4.2, true, fmt.Errorf("world"), "hello") -} - -func ExampleMust5() { - defer func() { - _ = recover() - }() - - // won't panic - Must5(42, "hello", 4.2, true, foo{}, nil) - - // will panic - Must5(42, "hello", 4.2, true, foo{}, fmt.Errorf("my error")) - - // will panic with error message - Must5(42, "hello", 4.2, true, foo{}, fmt.Errorf("world"), "hello") -} - -func ExampleMust6() { - defer func() { - _ = recover() - }() - - // won't panic - Must5(42, "hello", 4.2, true, foo{}, "foobar", nil) - - // will panic - Must5(42, "hello", 4.2, true, foo{}, "foobar", fmt.Errorf("my error")) - - // will panic with error message - Must5(42, "hello", 4.2, true, foo{}, "foobar", fmt.Errorf("world"), "hello") -} - -func ExampleTry() { - ok1 := Try(func() error { - return nil - }) - ok2 := Try(func() error { - return fmt.Errorf("my error") - }) - ok3 := Try(func() error { - panic("my error") - }) - - fmt.Printf("%v\n", ok1) - fmt.Printf("%v\n", ok2) - fmt.Printf("%v\n", ok3) - // Output: - // true - // false - // false -} - -func ExampleTry1() { - ok1 := Try1(func() error { - return nil - }) - ok2 := Try1(func() error { - return fmt.Errorf("my error") - }) - ok3 := Try1(func() error { - panic("my error") - }) - - fmt.Printf("%v\n", ok1) - fmt.Printf("%v\n", ok2) - fmt.Printf("%v\n", ok3) - // Output: - // true - // false - // false -} - -func ExampleTry2() { - ok1 := Try2(func() (int, error) { - return 42, nil - }) - ok2 := Try2(func() (int, error) { - return 42, fmt.Errorf("my error") - }) - ok3 := Try2(func() (int, error) { - panic("my error") - }) - - fmt.Printf("%v\n", ok1) - fmt.Printf("%v\n", ok2) - fmt.Printf("%v\n", ok3) - // Output: - // true - // false - // false -} - -func ExampleTry3() { - ok1 := Try3(func() (int, string, error) { - return 42, "foobar", nil - }) - ok2 := Try3(func() (int, string, error) { - return 42, "foobar", fmt.Errorf("my error") - }) - ok3 := Try3(func() (int, string, error) { - panic("my error") - }) - - fmt.Printf("%v\n", ok1) - fmt.Printf("%v\n", ok2) - fmt.Printf("%v\n", ok3) - // Output: - // true - // false - // false -} - -func ExampleTry4() { - ok1 := Try4(func() (int, string, float64, error) { - return 42, "foobar", 4.2, nil - }) - ok2 := Try4(func() (int, string, float64, error) { - return 42, "foobar", 4.2, fmt.Errorf("my error") - }) - ok3 := Try4(func() (int, string, float64, error) { - panic("my error") - }) - - fmt.Printf("%v\n", ok1) - fmt.Printf("%v\n", ok2) - fmt.Printf("%v\n", ok3) - // Output: - // true - // false - // false -} - -func ExampleTry5() { - ok1 := Try5(func() (int, string, float64, bool, error) { - return 42, "foobar", 4.2, true, nil - }) - ok2 := Try5(func() (int, string, float64, bool, error) { - return 42, "foobar", 4.2, true, fmt.Errorf("my error") - }) - ok3 := Try5(func() (int, string, float64, bool, error) { - panic("my error") - }) - - fmt.Printf("%v\n", ok1) - fmt.Printf("%v\n", ok2) - fmt.Printf("%v\n", ok3) - // Output: - // true - // false - // false -} - -func ExampleTry6() { - ok1 := Try6(func() (int, string, float64, bool, foo, error) { - return 42, "foobar", 4.2, true, foo{}, nil - }) - ok2 := Try6(func() (int, string, float64, bool, foo, error) { - return 42, "foobar", 4.2, true, foo{}, fmt.Errorf("my error") - }) - ok3 := Try6(func() (int, string, float64, bool, foo, error) { - panic("my error") - }) - - fmt.Printf("%v\n", ok1) - fmt.Printf("%v\n", ok2) - fmt.Printf("%v\n", ok3) - // Output: - // true - // false - // false -} - -func ExampleTryOr() { - value1, ok1 := TryOr(func() (int, error) { - return 42, nil - }, 21) - value2, ok2 := TryOr(func() (int, error) { - return 42, fmt.Errorf("my error") - }, 21) - value3, ok3 := TryOr(func() (int, error) { - panic("my error") - }, 21) - - fmt.Printf("%v %v\n", value1, ok1) - fmt.Printf("%v %v\n", value2, ok2) - fmt.Printf("%v %v\n", value3, ok3) - // Output: - // 42 true - // 21 false - // 21 false -} - -func ExampleTryOr1() { - value1, ok1 := TryOr1(func() (int, error) { - return 42, nil - }, 21) - value2, ok2 := TryOr1(func() (int, error) { - return 42, fmt.Errorf("my error") - }, 21) - value3, ok3 := TryOr1(func() (int, error) { - panic("my error") - }, 21) - - fmt.Printf("%v %v\n", value1, ok1) - fmt.Printf("%v %v\n", value2, ok2) - fmt.Printf("%v %v\n", value3, ok3) - // Output: - // 42 true - // 21 false - // 21 false -} - -func ExampleTryOr2() { - value1, value2, ok3 := TryOr2(func() (int, string, error) { - panic("my error") - }, 21, "hello") - - fmt.Printf("%v %v %v\n", value1, value2, ok3) - // Output: 21 hello false -} - -func ExampleTryOr3() { - value1, value2, value3, ok3 := TryOr3(func() (int, string, bool, error) { - panic("my error") - }, 21, "hello", false) - - fmt.Printf("%v %v %v %v\n", value1, value2, value3, ok3) - // Output: 21 hello false false -} - -func ExampleTryOr4() { - value1, value2, value3, value4, ok3 := TryOr4(func() (int, string, bool, foo, error) { - panic("my error") - }, 21, "hello", false, foo{bar: "bar"}) - - fmt.Printf("%v %v %v %v %v\n", value1, value2, value3, value4, ok3) - // Output: 21 hello false {bar} false -} - -func ExampleTryOr5() { - value1, value2, value3, value4, value5, ok3 := TryOr5(func() (int, string, bool, foo, float64, error) { - panic("my error") - }, 21, "hello", false, foo{bar: "bar"}, 4.2) - - fmt.Printf("%v %v %v %v %v %v\n", value1, value2, value3, value4, value5, ok3) - // Output: 21 hello false {bar} 4.2 false -} -func ExampleTryOr6() { - value1, value2, value3, value4, value5, value6, ok3 := TryOr6(func() (int, string, bool, foo, float64, string, error) { - panic("my error") - }, 21, "hello", false, foo{bar: "bar"}, 4.2, "world") - - fmt.Printf("%v %v %v %v %v %v %v\n", value1, value2, value3, value4, value5, value6, ok3) - // Output: 21 hello false {bar} 4.2 world false -} - -func ExampleTryWithErrorValue() { - err1, ok1 := TryWithErrorValue(func() error { - return nil - }) - err2, ok2 := TryWithErrorValue(func() error { - return fmt.Errorf("my error") - }) - err3, ok3 := TryWithErrorValue(func() error { - panic("my error") - }) - - fmt.Printf("%v %v\n", err1, ok1) - fmt.Printf("%v %v\n", err2, ok2) - fmt.Printf("%v %v\n", err3, ok3) - // Output: - // true - // my error false - // my error false -} - -func ExampleTryCatchWithErrorValue() { - TryCatchWithErrorValue( - func() error { - panic("trigger an error") - }, - func(err any) { - fmt.Printf("catch: %s", err) - }, - ) - - // Output: catch: trigger an error -} - -type myError struct { -} - -func (e myError) Error() string { - return "my error" -} - -func ExampleErrorsAs() { - doSomething := func() error { - return &myError{} - } - - err := doSomething() - - if rateLimitErr, ok := ErrorsAs[*myError](err); ok { - fmt.Printf("is type myError, err: %s", rateLimitErr.Error()) - } else { - fmt.Printf("is not type myError") - } - - // Output: is type myError, err: my error -} diff --git a/errors_test.go b/errors_test.go deleted file mode 100644 index 08cace9d..00000000 --- a/errors_test.go +++ /dev/null @@ -1,599 +0,0 @@ -package lo - -import ( - "errors" - "fmt" - "testing" - - "github.com/stretchr/testify/assert" -) - -func TestValidate(t *testing.T) { - is := assert.New(t) - - slice := []string{"a"} - result1 := Validate(len(slice) == 0, "Slice should be empty but contains %v", slice) - - slice = []string{} - result2 := Validate(len(slice) == 0, "Slice should be empty but contains %v", slice) - - is.Error(result1) - is.NoError(result2) -} - -func TestMust(t *testing.T) { - t.Parallel() - is := assert.New(t) - - is.Equal("foo", Must("foo", nil)) - is.PanicsWithValue("something went wrong", func() { - Must("", errors.New("something went wrong")) - }) - is.PanicsWithValue("operation shouldn't fail: something went wrong", func() { - Must("", errors.New("something went wrong"), "operation shouldn't fail") - }) - is.PanicsWithValue("operation shouldn't fail with foo: something went wrong", func() { - Must("", errors.New("something went wrong"), "operation shouldn't fail with %s", "foo") - }) - - is.Equal(1, Must(1, true)) - is.PanicsWithValue("not ok", func() { - Must(1, false) - }) - is.PanicsWithValue("operation shouldn't fail", func() { - Must(1, false, "operation shouldn't fail") - }) - is.PanicsWithValue("operation shouldn't fail with foo", func() { - Must(1, false, "operation shouldn't fail with %s", "foo") - }) - - cb := func() error { - return assert.AnError - } - is.PanicsWithValue("operation should fail: assert.AnError general error for testing", func() { - Must0(cb(), "operation should fail") - }) - - is.PanicsWithValue("must: invalid err type 'int', should either be a bool or an error", func() { - Must0(0) - }) - is.PanicsWithValue("must: invalid err type 'string', should either be a bool or an error", func() { - Must0("error") - }) -} - -func TestMustX(t *testing.T) { - t.Parallel() - is := assert.New(t) - - { - is.PanicsWithValue("something went wrong", func() { - Must0(errors.New("something went wrong")) - }) - is.PanicsWithValue("operation shouldn't fail with foo: something went wrong", func() { - Must0(errors.New("something went wrong"), "operation shouldn't fail with %s", "foo") - }) - is.NotPanics(func() { - Must0(nil) - }) - } - - { - val1 := Must1(1, nil) - is.Equal(1, val1) - is.PanicsWithValue("something went wrong", func() { - Must1(1, errors.New("something went wrong")) - }) - is.PanicsWithValue("operation shouldn't fail with foo: something went wrong", func() { - Must1(1, errors.New("something went wrong"), "operation shouldn't fail with %s", "foo") - }) - } - - { - val1, val2 := Must2(1, 2, nil) - is.Equal(1, val1) - is.Equal(2, val2) - is.PanicsWithValue("something went wrong", func() { - Must2(1, 2, errors.New("something went wrong")) - }) - is.PanicsWithValue("operation shouldn't fail with foo: something went wrong", func() { - Must2(1, 2, errors.New("something went wrong"), "operation shouldn't fail with %s", "foo") - }) - } - - { - val1, val2, val3 := Must3(1, 2, 3, nil) - is.Equal(1, val1) - is.Equal(2, val2) - is.Equal(3, val3) - is.PanicsWithValue("something went wrong", func() { - Must3(1, 2, 3, errors.New("something went wrong")) - }) - is.PanicsWithValue("operation shouldn't fail with foo: something went wrong", func() { - Must3(1, 2, 3, errors.New("something went wrong"), "operation shouldn't fail with %s", "foo") - }) - } - - { - val1, val2, val3, val4 := Must4(1, 2, 3, 4, nil) - is.Equal(1, val1) - is.Equal(2, val2) - is.Equal(3, val3) - is.Equal(4, val4) - is.PanicsWithValue("something went wrong", func() { - Must4(1, 2, 3, 4, errors.New("something went wrong")) - }) - is.PanicsWithValue("operation shouldn't fail with foo: something went wrong", func() { - Must4(1, 2, 3, 4, errors.New("something went wrong"), "operation shouldn't fail with %s", "foo") - }) - } - - { - val1, val2, val3, val4, val5 := Must5(1, 2, 3, 4, 5, nil) - is.Equal(1, val1) - is.Equal(2, val2) - is.Equal(3, val3) - is.Equal(4, val4) - is.Equal(5, val5) - is.PanicsWithValue("something went wrong", func() { - Must5(1, 2, 3, 4, 5, errors.New("something went wrong")) - }) - is.PanicsWithValue("operation shouldn't fail with foo: something went wrong", func() { - Must5(1, 2, 3, 4, 5, errors.New("something went wrong"), "operation shouldn't fail with %s", "foo") - }) - } - - { - val1, val2, val3, val4, val5, val6 := Must6(1, 2, 3, 4, 5, 6, nil) - is.Equal(1, val1) - is.Equal(2, val2) - is.Equal(3, val3) - is.Equal(4, val4) - is.Equal(5, val5) - is.Equal(6, val6) - is.PanicsWithValue("something went wrong", func() { - Must6(1, 2, 3, 4, 5, 6, errors.New("something went wrong")) - }) - is.PanicsWithValue("operation shouldn't fail with foo: something went wrong", func() { - Must6(1, 2, 3, 4, 5, 6, errors.New("something went wrong"), "operation shouldn't fail with %s", "foo") - }) - } - - { - is.PanicsWithValue("not ok", func() { - Must0(false) - }) - is.PanicsWithValue("operation shouldn't fail with foo", func() { - Must0(false, "operation shouldn't fail with %s", "foo") - }) - is.NotPanics(func() { - Must0(true) - }) - } - - { - val1 := Must1(1, true) - is.Equal(1, val1) - is.PanicsWithValue("not ok", func() { - Must1(1, false) - }) - is.PanicsWithValue("operation shouldn't fail with foo", func() { - Must1(1, false, "operation shouldn't fail with %s", "foo") - }) - } - - { - val1, val2 := Must2(1, 2, true) - is.Equal(1, val1) - is.Equal(2, val2) - is.PanicsWithValue("not ok", func() { - Must2(1, 2, false) - }) - is.PanicsWithValue("operation shouldn't fail with foo", func() { - Must2(1, 2, false, "operation shouldn't fail with %s", "foo") - }) - } - - { - val1, val2, val3 := Must3(1, 2, 3, true) - is.Equal(1, val1) - is.Equal(2, val2) - is.Equal(3, val3) - is.PanicsWithValue("not ok", func() { - Must3(1, 2, 3, false) - }) - is.PanicsWithValue("operation shouldn't fail with foo", func() { - Must3(1, 2, 3, false, "operation shouldn't fail with %s", "foo") - }) - } - - { - val1, val2, val3, val4 := Must4(1, 2, 3, 4, true) - is.Equal(1, val1) - is.Equal(2, val2) - is.Equal(3, val3) - is.Equal(4, val4) - is.PanicsWithValue("not ok", func() { - Must4(1, 2, 3, 4, false) - }) - is.PanicsWithValue("operation shouldn't fail with foo", func() { - Must4(1, 2, 3, 4, false, "operation shouldn't fail with %s", "foo") - }) - } - - { - val1, val2, val3, val4, val5 := Must5(1, 2, 3, 4, 5, true) - is.Equal(1, val1) - is.Equal(2, val2) - is.Equal(3, val3) - is.Equal(4, val4) - is.Equal(5, val5) - is.PanicsWithValue("not ok", func() { - Must5(1, 2, 3, 4, 5, false) - }) - is.PanicsWithValue("operation shouldn't fail with foo", func() { - Must5(1, 2, 3, 4, 5, false, "operation shouldn't fail with %s", "foo") - }) - } - - { - val1, val2, val3, val4, val5, val6 := Must6(1, 2, 3, 4, 5, 6, true) - is.Equal(1, val1) - is.Equal(2, val2) - is.Equal(3, val3) - is.Equal(4, val4) - is.Equal(5, val5) - is.Equal(6, val6) - is.PanicsWithValue("not ok", func() { - Must6(1, 2, 3, 4, 5, 6, false) - }) - is.PanicsWithValue("operation shouldn't fail with foo", func() { - Must6(1, 2, 3, 4, 5, 6, false, "operation shouldn't fail with %s", "foo") - }) - } -} - -func TestTry(t *testing.T) { - t.Parallel() - is := assert.New(t) - - is.False(Try(func() error { - panic("error") - })) - is.True(Try(func() error { - return nil - })) - is.False(Try(func() error { - return fmt.Errorf("fail") - })) -} - -func TestTryX(t *testing.T) { - t.Parallel() - is := assert.New(t) - - is.True(Try1(func() error { - return nil - })) - - is.True(Try2(func() (string, error) { - return "", nil - })) - - is.True(Try3(func() (string, string, error) { - return "", "", nil - })) - - is.True(Try4(func() (string, string, string, error) { - return "", "", "", nil - })) - - is.True(Try5(func() (string, string, string, string, error) { - return "", "", "", "", nil - })) - - is.True(Try6(func() (string, string, string, string, string, error) { - return "", "", "", "", "", nil - })) - - is.False(Try1(func() error { - panic("error") - })) - - is.False(Try2(func() (string, error) { - panic("error") - })) - - is.False(Try3(func() (string, string, error) { - panic("error") - })) - - is.False(Try4(func() (string, string, string, error) { - panic("error") - })) - - is.False(Try5(func() (string, string, string, string, error) { - panic("error") - })) - - is.False(Try6(func() (string, string, string, string, string, error) { - panic("error") - })) - - is.False(Try1(func() error { - return errors.New("foo") - })) - - is.False(Try2(func() (string, error) { - return "", errors.New("foo") - })) - - is.False(Try3(func() (string, string, error) { - return "", "", errors.New("foo") - })) - - is.False(Try4(func() (string, string, string, error) { - return "", "", "", errors.New("foo") - })) - - is.False(Try5(func() (string, string, string, string, error) { - return "", "", "", "", errors.New("foo") - })) - - is.False(Try6(func() (string, string, string, string, string, error) { - return "", "", "", "", "", errors.New("foo") - })) -} - -func TestTryOr(t *testing.T) { - t.Parallel() - is := assert.New(t) - - a1, ok1 := TryOr(func() (int, error) { panic("error") }, 42) - a2, ok2 := TryOr(func() (int, error) { return 21, assert.AnError }, 42) - a3, ok3 := TryOr(func() (int, error) { return 21, nil }, 42) - - is.Equal(42, a1) - is.False(ok1) - - is.Equal(42, a2) - is.False(ok2) - - is.Equal(21, a3) - is.True(ok3) -} - -func TestTryOrX(t *testing.T) { - t.Parallel() - is := assert.New(t) - - { - a1, ok1 := TryOr1(func() (int, error) { panic("error") }, 42) - a2, ok2 := TryOr1(func() (int, error) { return 21, assert.AnError }, 42) - a3, ok3 := TryOr1(func() (int, error) { return 21, nil }, 42) - - is.Equal(42, a1) - is.False(ok1) - - is.Equal(42, a2) - is.False(ok2) - - is.Equal(21, a3) - is.True(ok3) - } - - { - a1, b1, ok1 := TryOr2(func() (int, string, error) { panic("error") }, 42, "hello") - a2, b2, ok2 := TryOr2(func() (int, string, error) { return 21, "world", assert.AnError }, 42, "hello") - a3, b3, ok3 := TryOr2(func() (int, string, error) { return 21, "world", nil }, 42, "hello") - - is.Equal(42, a1) - is.Equal("hello", b1) - is.False(ok1) - - is.Equal(42, a2) - is.Equal("hello", b2) - is.False(ok2) - - is.Equal(21, a3) - is.Equal("world", b3) - is.True(ok3) - } - - { - a1, b1, c1, ok1 := TryOr3(func() (int, string, bool, error) { panic("error") }, 42, "hello", false) - a2, b2, c2, ok2 := TryOr3(func() (int, string, bool, error) { return 21, "world", true, assert.AnError }, 42, "hello", false) - a3, b3, c3, ok3 := TryOr3(func() (int, string, bool, error) { return 21, "world", true, nil }, 42, "hello", false) - - is.Equal(42, a1) - is.Equal("hello", b1) - is.Equal(false, c1) - is.False(ok1) - - is.Equal(42, a2) - is.Equal("hello", b2) - is.Equal(false, c2) - is.False(ok2) - - is.Equal(21, a3) - is.Equal("world", b3) - is.Equal(true, c3) - is.True(ok3) - } - - { - a1, b1, c1, d1, ok1 := TryOr4(func() (int, string, bool, int, error) { panic("error") }, 42, "hello", false, 42) - a2, b2, c2, d2, ok2 := TryOr4(func() (int, string, bool, int, error) { return 21, "world", true, 21, assert.AnError }, 42, "hello", false, 42) - a3, b3, c3, d3, ok3 := TryOr4(func() (int, string, bool, int, error) { return 21, "world", true, 21, nil }, 42, "hello", false, 42) - - is.Equal(42, a1) - is.Equal("hello", b1) - is.Equal(false, c1) - is.Equal(42, d1) - is.False(ok1) - - is.Equal(42, a2) - is.Equal("hello", b2) - is.Equal(false, c2) - is.Equal(42, d2) - is.False(ok2) - - is.Equal(21, a3) - is.Equal("world", b3) - is.Equal(true, c3) - is.Equal(21, d3) - is.True(ok3) - } - - { - a1, b1, c1, d1, e1, ok1 := TryOr5(func() (int, string, bool, int, int, error) { panic("error") }, 42, "hello", false, 42, 42) - a2, b2, c2, d2, e2, ok2 := TryOr5(func() (int, string, bool, int, int, error) { return 21, "world", true, 21, 21, assert.AnError }, 42, "hello", false, 42, 42) - a3, b3, c3, d3, e3, ok3 := TryOr5(func() (int, string, bool, int, int, error) { return 21, "world", true, 21, 21, nil }, 42, "hello", false, 42, 42) - - is.Equal(42, a1) - is.Equal("hello", b1) - is.Equal(false, c1) - is.Equal(42, d1) - is.Equal(42, e1) - is.False(ok1) - - is.Equal(42, a2) - is.Equal("hello", b2) - is.Equal(false, c2) - is.Equal(42, d2) - is.Equal(42, e2) - is.False(ok2) - - is.Equal(21, a3) - is.Equal("world", b3) - is.Equal(true, c3) - is.Equal(21, d3) - is.Equal(21, e3) - is.True(ok3) - } - - { - a1, b1, c1, d1, e1, f1, ok1 := TryOr6(func() (int, string, bool, int, int, int, error) { panic("error") }, 42, "hello", false, 42, 42, 42) - a2, b2, c2, d2, e2, f2, ok2 := TryOr6(func() (int, string, bool, int, int, int, error) { return 21, "world", true, 21, 21, 21, assert.AnError }, 42, "hello", false, 42, 42, 42) - a3, b3, c3, d3, e3, f3, ok3 := TryOr6(func() (int, string, bool, int, int, int, error) { return 21, "world", true, 21, 21, 21, nil }, 42, "hello", false, 42, 42, 42) - - is.Equal(42, a1) - is.Equal("hello", b1) - is.Equal(false, c1) - is.Equal(42, d1) - is.Equal(42, e1) - is.Equal(42, f1) - is.False(ok1) - - is.Equal(42, a2) - is.Equal("hello", b2) - is.Equal(false, c2) - is.Equal(42, d2) - is.Equal(42, e2) - is.Equal(42, f2) - is.False(ok2) - - is.Equal(21, a3) - is.Equal("world", b3) - is.Equal(true, c3) - is.Equal(21, d3) - is.Equal(21, e3) - is.Equal(21, f3) - is.True(ok3) - } -} - -func TestTryWithErrorValue(t *testing.T) { - t.Parallel() - is := assert.New(t) - - err, ok := TryWithErrorValue(func() error { - // getting error in case of panic, using recover function - panic("error") - }) - is.False(ok) - is.Equal("error", err) - - err, ok = TryWithErrorValue(func() error { - return errors.New("foo") - }) - is.False(ok) - is.EqualError(err.(error), "foo") - - err, ok = TryWithErrorValue(func() error { - return nil - }) - is.True(ok) - is.Equal(nil, err) -} - -func TestTryCatch(t *testing.T) { - t.Parallel() - is := assert.New(t) - - caught := false - TryCatch(func() error { - panic("error") - }, func() { - //error was caught - caught = true - }) - is.True(caught) - - caught = false - TryCatch(func() error { - return nil - }, func() { - //no error to be caught - caught = true - }) - is.False(caught) -} - -func TestTryCatchWithErrorValue(t *testing.T) { - t.Parallel() - is := assert.New(t) - - caught := false - TryCatchWithErrorValue(func() error { - panic("error") - }, func(val any) { - //error was caught - caught = val == "error" - }) - is.True(caught) - - caught = false - TryCatchWithErrorValue(func() error { - return nil - }, func(val any) { - //no error to be caught - caught = true - }) - is.False(caught) -} - -type internalError struct { - foobar string -} - -func (e *internalError) Error() string { - return "internal error" -} - -func TestErrorsAs(t *testing.T) { - t.Parallel() - is := assert.New(t) - - err, ok := ErrorsAs[*internalError](fmt.Errorf("hello world")) - is.False(ok) - is.Nil(nil, err) - - err, ok = ErrorsAs[*internalError](&internalError{foobar: "foobar"}) - is.True(ok) - is.Equal(&internalError{foobar: "foobar"}, err) - - err, ok = ErrorsAs[*internalError](nil) - is.False(ok) - is.Nil(nil, err) -} diff --git a/find_test.go b/find_test.go deleted file mode 100644 index 35f51799..00000000 --- a/find_test.go +++ /dev/null @@ -1,396 +0,0 @@ -package lo - -import ( - "fmt" - "math/rand" - "sort" - "testing" - "time" - - "github.com/stretchr/testify/assert" -) - -func TestIndexOf(t *testing.T) { - t.Parallel() - is := assert.New(t) - - result1 := IndexOf([]int{0, 1, 2, 1, 2, 3}, 2) - result2 := IndexOf([]int{0, 1, 2, 1, 2, 3}, 6) - - is.Equal(result1, 2) - is.Equal(result2, -1) -} - -func TestLastIndexOf(t *testing.T) { - t.Parallel() - is := assert.New(t) - - result1 := LastIndexOf([]int{0, 1, 2, 1, 2, 3}, 2) - result2 := LastIndexOf([]int{0, 1, 2, 1, 2, 3}, 6) - - is.Equal(result1, 4) - is.Equal(result2, -1) -} - -func TestFind(t *testing.T) { - t.Parallel() - is := assert.New(t) - - index := 0 - result1, ok1 := Find([]string{"a", "b", "c", "d"}, func(item string) bool { - is.Equal([]string{"a", "b", "c", "d"}[index], item) - index++ - return item == "b" - }) - - result2, ok2 := Find([]string{"foobar"}, func(item string) bool { - is.Equal("foobar", item) - return item == "b" - }) - - is.Equal(ok1, true) - is.Equal(result1, "b") - is.Equal(ok2, false) - is.Equal(result2, "") -} - -func TestFindIndexOf(t *testing.T) { - t.Parallel() - is := assert.New(t) - - index := 0 - item1, index1, ok1 := FindIndexOf([]string{"a", "b", "c", "d", "b"}, func(item string) bool { - is.Equal([]string{"a", "b", "c", "d", "b"}[index], item) - index++ - return item == "b" - }) - item2, index2, ok2 := FindIndexOf([]string{"foobar"}, func(item string) bool { - is.Equal("foobar", item) - return item == "b" - }) - - is.Equal(item1, "b") - is.Equal(ok1, true) - is.Equal(index1, 1) - is.Equal(item2, "") - is.Equal(ok2, false) - is.Equal(index2, -1) -} - -func TestFindLastIndexOf(t *testing.T) { - t.Parallel() - is := assert.New(t) - - index := 0 - item1, index1, ok1 := FindLastIndexOf([]string{"a", "b", "c", "d", "b"}, func(item string) bool { - is.Equal([]string{"b", "d", "c", "b", "a"}[index], item) - index++ - return item == "b" - }) - item2, index2, ok2 := FindLastIndexOf([]string{"foobar"}, func(item string) bool { - is.Equal("foobar", item) - return item == "b" - }) - - is.Equal(item1, "b") - is.Equal(ok1, true) - is.Equal(index1, 4) - is.Equal(item2, "") - is.Equal(ok2, false) - is.Equal(index2, -1) -} - -func TestFindOrElse(t *testing.T) { - t.Parallel() - is := assert.New(t) - - index := 0 - result1 := FindOrElse([]string{"a", "b", "c", "d"}, "x", func(item string) bool { - is.Equal([]string{"a", "b", "c", "d"}[index], item) - index++ - return item == "b" - }) - result2 := FindOrElse([]string{"foobar"}, "x", func(item string) bool { - is.Equal("foobar", item) - return item == "b" - }) - - is.Equal(result1, "b") - is.Equal(result2, "x") -} - -func TestFindKey(t *testing.T) { - t.Parallel() - is := assert.New(t) - - result1, ok1 := FindKey(map[string]int{"foo": 1, "bar": 2, "baz": 3}, 2) - is.Equal("bar", result1) - is.True(ok1) - - result2, ok2 := FindKey(map[string]int{"foo": 1, "bar": 2, "baz": 3}, 42) - is.Equal("", result2) - is.False(ok2) - - type test struct { - foobar string - } - - result3, ok3 := FindKey(map[string]test{"foo": {"foo"}, "bar": {"bar"}, "baz": {"baz"}}, test{"foo"}) - is.Equal("foo", result3) - is.True(ok3) - - result4, ok4 := FindKey(map[string]test{"foo": {"foo"}, "bar": {"bar"}, "baz": {"baz"}}, test{"hello world"}) - is.Equal("", result4) - is.False(ok4) -} - -func TestFindKeyBy(t *testing.T) { - t.Parallel() - is := assert.New(t) - - result1, ok1 := FindKeyBy(map[string]int{"foo": 1, "bar": 2, "baz": 3}, func(k string, v int) bool { - return k == "foo" - }) - is.Equal("foo", result1) - is.True(ok1) - - result2, ok2 := FindKeyBy(map[string]int{"foo": 1, "bar": 2, "baz": 3}, func(k string, v int) bool { - return false - }) - is.Equal("", result2) - is.False(ok2) -} - -func TestFindUniques(t *testing.T) { - t.Parallel() - is := assert.New(t) - - result1 := FindUniques([]int{1, 2, 3}) - - is.Equal(3, len(result1)) - is.Equal([]int{1, 2, 3}, result1) - - result2 := FindUniques([]int{1, 2, 2, 3, 1, 2}) - - is.Equal(1, len(result2)) - is.Equal([]int{3}, result2) - - result3 := FindUniques([]int{1, 2, 2, 1}) - - is.Equal(0, len(result3)) - is.Equal([]int{}, result3) - - result4 := FindUniques([]int{}) - - is.Equal(0, len(result4)) - is.Equal([]int{}, result4) -} - -func TestFindUniquesBy(t *testing.T) { - t.Parallel() - is := assert.New(t) - - result1 := FindUniquesBy([]int{0, 1, 2}, func(i int) int { - return i % 3 - }) - - is.Equal(3, len(result1)) - is.Equal([]int{0, 1, 2}, result1) - - result2 := FindUniquesBy([]int{0, 1, 2, 3, 4}, func(i int) int { - return i % 3 - }) - - is.Equal(1, len(result2)) - is.Equal([]int{2}, result2) - - result3 := FindUniquesBy([]int{0, 1, 2, 3, 4, 5}, func(i int) int { - return i % 3 - }) - - is.Equal(0, len(result3)) - is.Equal([]int{}, result3) - - result4 := FindUniquesBy([]int{}, func(i int) int { - return i % 3 - }) - - is.Equal(0, len(result4)) - is.Equal([]int{}, result4) -} - -func TestFindDuplicates(t *testing.T) { - t.Parallel() - is := assert.New(t) - - result1 := FindDuplicates([]int{1, 2, 2, 1, 2, 3}) - - is.Equal(2, len(result1)) - is.Equal([]int{1, 2}, result1) - - result2 := FindDuplicates([]int{1, 2, 3}) - - is.Equal(0, len(result2)) - is.Equal([]int{}, result2) - - result3 := FindDuplicates([]int{}) - - is.Equal(0, len(result3)) - is.Equal([]int{}, result3) -} - -func TestFindDuplicatesBy(t *testing.T) { - t.Parallel() - is := assert.New(t) - - result1 := FindDuplicatesBy([]int{3, 4, 5, 6, 7}, func(i int) int { - return i % 3 - }) - - is.Equal(2, len(result1)) - is.Equal([]int{3, 4}, result1) - - result2 := FindDuplicatesBy([]int{0, 1, 2, 3, 4}, func(i int) int { - return i % 5 - }) - - is.Equal(0, len(result2)) - is.Equal([]int{}, result2) - - result3 := FindDuplicatesBy([]int{}, func(i int) int { - return i % 3 - }) - - is.Equal(0, len(result3)) - is.Equal([]int{}, result3) -} - -func TestMin(t *testing.T) { - t.Parallel() - is := assert.New(t) - - result1 := Min([]int{1, 2, 3}) - result2 := Min([]int{3, 2, 1}) - result3 := Min([]int{}) - - is.Equal(result1, 1) - is.Equal(result2, 1) - is.Equal(result3, 0) -} - -func TestMinBy(t *testing.T) { - t.Parallel() - is := assert.New(t) - - result1 := MinBy([]string{"s1", "string2", "s3"}, func(item string, min string) bool { - return len(item) < len(min) - }) - result2 := MinBy([]string{"string1", "string2", "s3"}, func(item string, min string) bool { - return len(item) < len(min) - }) - result3 := MinBy([]string{}, func(item string, min string) bool { - return len(item) < len(min) - }) - - is.Equal(result1, "s1") - is.Equal(result2, "s3") - is.Equal(result3, "") -} - -func TestMax(t *testing.T) { - t.Parallel() - is := assert.New(t) - - result1 := Max([]int{1, 2, 3}) - result2 := Max([]int{3, 2, 1}) - result3 := Max([]int{}) - - is.Equal(result1, 3) - is.Equal(result2, 3) - is.Equal(result3, 0) -} - -func TestMaxBy(t *testing.T) { - t.Parallel() - is := assert.New(t) - - result1 := MaxBy([]string{"s1", "string2", "s3"}, func(item string, max string) bool { - return len(item) > len(max) - }) - result2 := MaxBy([]string{"string1", "string2", "s3"}, func(item string, max string) bool { - return len(item) > len(max) - }) - result3 := MaxBy([]string{}, func(item string, max string) bool { - return len(item) > len(max) - }) - - is.Equal(result1, "string2") - is.Equal(result2, "string1") - is.Equal(result3, "") -} - -func TestLast(t *testing.T) { - t.Parallel() - is := assert.New(t) - - result1, err1 := Last([]int{1, 2, 3}) - result2, err2 := Last([]int{}) - - is.Equal(result1, 3) - is.Equal(err1, nil) - is.Equal(result2, 0) - is.Equal(err2, fmt.Errorf("last: cannot extract the last element of an empty slice")) -} - -func TestNth(t *testing.T) { - t.Parallel() - is := assert.New(t) - - result1, err1 := Nth([]int{0, 1, 2, 3}, 2) - result2, err2 := Nth([]int{0, 1, 2, 3}, -2) - result3, err3 := Nth([]int{0, 1, 2, 3}, 42) - result4, err4 := Nth([]int{}, 0) - result5, err5 := Nth([]int{42}, 0) - result6, err6 := Nth([]int{42}, -1) - - is.Equal(result1, 2) - is.Equal(err1, nil) - is.Equal(result2, 2) - is.Equal(err2, nil) - is.Equal(result3, 0) - is.Equal(err3, fmt.Errorf("nth: 42 out of slice bounds")) - is.Equal(result4, 0) - is.Equal(err4, fmt.Errorf("nth: 0 out of slice bounds")) - is.Equal(result5, 42) - is.Equal(err5, nil) - is.Equal(result6, 42) - is.Equal(err6, nil) -} - -func TestSample(t *testing.T) { - t.Parallel() - is := assert.New(t) - - rand.Seed(time.Now().UnixNano()) - - result1 := Sample([]string{"a", "b", "c"}) - result2 := Sample([]string{}) - - is.True(Contains([]string{"a", "b", "c"}, result1)) - is.Equal(result2, "") -} - -func TestSamples(t *testing.T) { - t.Parallel() - is := assert.New(t) - - rand.Seed(time.Now().UnixNano()) - - result1 := Samples([]string{"a", "b", "c"}, 3) - result2 := Samples([]string{}, 3) - - sort.Strings(result1) - - is.Equal(result1, []string{"a", "b", "c"}) - is.Equal(result2, []string{}) -} diff --git a/func_test.go b/func_test.go deleted file mode 100644 index 284d24a4..00000000 --- a/func_test.go +++ /dev/null @@ -1,80 +0,0 @@ -package lo - -import ( - "strconv" - "testing" - - "github.com/stretchr/testify/assert" -) - -func TestPartial(t *testing.T) { - t.Parallel() - is := assert.New(t) - - add := func(x float64, y int) string { - return strconv.Itoa(int(x) + y) - } - f := Partial(add, 5) - is.Equal("15", f(10)) - is.Equal("0", f(-5)) -} - -func TestPartial1(t *testing.T) { - t.Parallel() - is := assert.New(t) - - add := func(x float64, y int) string { - return strconv.Itoa(int(x) + y) - } - f := Partial1(add, 5) - is.Equal("15", f(10)) - is.Equal("0", f(-5)) -} - -func TestPartial2(t *testing.T) { - t.Parallel() - is := assert.New(t) - - add := func(x float64, y int, z int) string { - return strconv.Itoa(int(x) + y + z) - } - f := Partial2(add, 5) - is.Equal("24", f(10, 9)) - is.Equal("8", f(-5, 8)) -} - -func TestPartial3(t *testing.T) { - t.Parallel() - is := assert.New(t) - - add := func(x float64, y int, z int, a float32) string { - return strconv.Itoa(int(x) + y + z + int(a)) - } - f := Partial3(add, 5) - is.Equal("21", f(10, 9, -3)) - is.Equal("15", f(-5, 8, 7)) -} - -func TestPartial4(t *testing.T) { - t.Parallel() - is := assert.New(t) - - add := func(x float64, y int, z int, a float32, b int32) string { - return strconv.Itoa(int(x) + y + z + int(a) + int(b)) - } - f := Partial4(add, 5) - is.Equal("21", f(10, 9, -3, 0)) - is.Equal("14", f(-5, 8, 7, -1)) -} - -func TestPartial5(t *testing.T) { - t.Parallel() - is := assert.New(t) - - add := func(x float64, y int, z int, a float32, b int32, c int) string { - return strconv.Itoa(int(x) + y + z + int(a) + int(b) + c) - } - f := Partial5(add, 5) - is.Equal("26", f(10, 9, -3, 0, 5)) - is.Equal("21", f(-5, 8, 7, -1, 7)) -} diff --git a/go.mod b/go.mod index 9a767c06..26cd7be6 100644 --- a/go.mod +++ b/go.mod @@ -6,17 +6,4 @@ go 1.18 // Dependencies are excluded from releases. Please check CI. // -require ( - github.com/stretchr/testify v1.8.0 - github.com/thoas/go-funk v0.9.1 - golang.org/x/exp v0.0.0-20220303212507-bbda1eaf7a17 -) - -require ( - github.com/davecgh/go-spew v1.1.1 // indirect - github.com/kr/text v0.2.0 // indirect - github.com/niemeyer/pretty v0.0.0-20200227124842-a10e7caefd8e // indirect - github.com/pmezard/go-difflib v1.0.0 // indirect - gopkg.in/check.v1 v1.0.0-20200227125254-8fa46927fb4f // indirect - gopkg.in/yaml.v3 v3.0.1 // indirect -) +require golang.org/x/exp v0.0.0-20220303212507-bbda1eaf7a17 diff --git a/go.sum b/go.sum index cc231827..d4656cf7 100644 --- a/go.sum +++ b/go.sum @@ -1,29 +1,2 @@ -github.com/creack/pty v1.1.9/go.mod h1:oKZEueFk5CKHvIhNR5MUki03XCEU+Q6VDXinZuGJ33E= -github.com/davecgh/go-spew v1.1.0/go.mod h1:J7Y8YcW2NihsgmVo/mv3lAwl/skON4iLHjSsI+c5H38= -github.com/davecgh/go-spew v1.1.1 h1:vj9j/u1bqnvCEfJOwUhtlOARqs3+rkHYY13jYWTU97c= -github.com/davecgh/go-spew v1.1.1/go.mod h1:J7Y8YcW2NihsgmVo/mv3lAwl/skON4iLHjSsI+c5H38= -github.com/kr/pty v1.1.1/go.mod h1:pFQYn66WHrOpPYNljwOMqo10TkYh1fy3cYio2l3bCsQ= -github.com/kr/text v0.1.0/go.mod h1:4Jbv+DJW3UT/LiOwJeYQe1efqtUx/iVham/4vfdArNI= -github.com/kr/text v0.2.0 h1:5Nx0Ya0ZqY2ygV366QzturHI13Jq95ApcVaJBhpS+AY= -github.com/kr/text v0.2.0/go.mod h1:eLer722TekiGuMkidMxC/pM04lWEeraHUUmBw8l2grE= -github.com/niemeyer/pretty v0.0.0-20200227124842-a10e7caefd8e h1:fD57ERR4JtEqsWbfPhv4DMiApHyliiK5xCTNVSPiaAs= -github.com/niemeyer/pretty v0.0.0-20200227124842-a10e7caefd8e/go.mod h1:zD1mROLANZcx1PVRCS0qkT7pwLkGfwJo4zjcN/Tysno= -github.com/pmezard/go-difflib v1.0.0 h1:4DBwDE0NGyQoBHbLQYPwSUPoCMWR5BEzIk/f1lZbAQM= -github.com/pmezard/go-difflib v1.0.0/go.mod h1:iKH77koFhYxTK1pcRnkKkqfTogsbg7gZNVY4sRDYZ/4= -github.com/stretchr/objx v0.1.0/go.mod h1:HFkY916IF+rwdDfMAkV7OtwuqBVzrE8GR6GFx+wExME= -github.com/stretchr/objx v0.4.0/go.mod h1:YvHI0jy2hoMjB+UWwv71VJQ9isScKT/TqJzVSSt89Yw= -github.com/stretchr/testify v1.4.0/go.mod h1:j7eGeouHqKxXV5pUuKE4zz7dFj8WfuZ+81PSLYec5m4= -github.com/stretchr/testify v1.7.1/go.mod h1:6Fq8oRcR53rry900zMqJjRRixrwX3KX962/h/Wwjteg= -github.com/stretchr/testify v1.8.0 h1:pSgiaMZlXftHpm5L7V1+rVB+AZJydKsMxsQBIJw4PKk= -github.com/stretchr/testify v1.8.0/go.mod h1:yNjHg4UonilssWZ8iaSj1OCr/vHnekPRkoO+kdMU+MU= -github.com/thoas/go-funk v0.9.1 h1:O549iLZqPpTUQ10ykd26sZhzD+rmR5pWhuElrhbC20M= -github.com/thoas/go-funk v0.9.1/go.mod h1:+IWnUfUmFO1+WVYQWQtIJHeRRdaIyyYglZN7xzUPe4Q= golang.org/x/exp v0.0.0-20220303212507-bbda1eaf7a17 h1:3MTrJm4PyNL9NBqvYDSj3DHl46qQakyfqfWo4jgfaEM= golang.org/x/exp v0.0.0-20220303212507-bbda1eaf7a17/go.mod h1:lgLbSvA5ygNOMpwM/9anMpWVlVJ7Z+cHWq/eFuinpGE= -gopkg.in/check.v1 v0.0.0-20161208181325-20d25e280405/go.mod h1:Co6ibVJAznAaIkqp8huTwlJQCZ016jof/cbN4VW5Yz0= -gopkg.in/check.v1 v1.0.0-20200227125254-8fa46927fb4f h1:BLraFXnmrev5lT+xlilqcH8XK9/i0At2xKjWk4p6zsU= -gopkg.in/check.v1 v1.0.0-20200227125254-8fa46927fb4f/go.mod h1:Co6ibVJAznAaIkqp8huTwlJQCZ016jof/cbN4VW5Yz0= -gopkg.in/yaml.v2 v2.2.2/go.mod h1:hI93XBmqTisBFMUTm0b8Fm+jr3Dg1NNxqwp+5A1VGuI= -gopkg.in/yaml.v3 v3.0.0-20200313102051-9f266ea9e77c/go.mod h1:K4uyk7z7BCEPqu6E+C64Yfv1cQ7kz7rIZviUmN+EgEM= -gopkg.in/yaml.v3 v3.0.1 h1:fxVm/GzAzEWqLHuvctI91KS9hhNmmWOoWu0XTYJS7CA= -gopkg.in/yaml.v3 v3.0.1/go.mod h1:K4uyk7z7BCEPqu6E+C64Yfv1cQ7kz7rIZviUmN+EgEM= diff --git a/img/README.md b/img/README.md deleted file mode 100644 index 11219739..00000000 --- a/img/README.md +++ /dev/null @@ -1,2 +0,0 @@ - -Credits goes to https://gopherize.me/ \ No newline at end of file diff --git a/img/logo-full.png b/img/logo-full.png deleted file mode 100644 index 8dca0315..00000000 Binary files a/img/logo-full.png and /dev/null differ diff --git a/img/logo-full.xcf b/img/logo-full.xcf deleted file mode 100644 index a2913567..00000000 Binary files a/img/logo-full.xcf and /dev/null differ diff --git a/img/logo.png b/img/logo.png deleted file mode 100644 index 03d535b5..00000000 Binary files a/img/logo.png and /dev/null differ diff --git a/intersect_test.go b/intersect_test.go deleted file mode 100644 index 339dbcbb..00000000 --- a/intersect_test.go +++ /dev/null @@ -1,262 +0,0 @@ -package lo - -import ( - "testing" - - "github.com/stretchr/testify/assert" -) - -func TestContains(t *testing.T) { - t.Parallel() - is := assert.New(t) - - result1 := Contains([]int{0, 1, 2, 3, 4, 5}, 5) - result2 := Contains([]int{0, 1, 2, 3, 4, 5}, 6) - - is.Equal(result1, true) - is.Equal(result2, false) -} - -func TestContainsBy(t *testing.T) { - t.Parallel() - is := assert.New(t) - - type a struct { - A int - B string - } - - a1 := []a{{A: 1, B: "1"}, {A: 2, B: "2"}, {A: 3, B: "3"}} - result1 := ContainsBy(a1, func(t a) bool { return t.A == 1 && t.B == "2" }) - result2 := ContainsBy(a1, func(t a) bool { return t.A == 2 && t.B == "2" }) - - a2 := []string{"aaa", "bbb", "ccc"} - result3 := ContainsBy(a2, func(t string) bool { return t == "ccc" }) - result4 := ContainsBy(a2, func(t string) bool { return t == "ddd" }) - - is.Equal(result1, false) - is.Equal(result2, true) - is.Equal(result3, true) - is.Equal(result4, false) -} - -func TestEvery(t *testing.T) { - t.Parallel() - is := assert.New(t) - - result1 := Every([]int{0, 1, 2, 3, 4, 5}, []int{0, 2}) - result2 := Every([]int{0, 1, 2, 3, 4, 5}, []int{0, 6}) - result3 := Every([]int{0, 1, 2, 3, 4, 5}, []int{-1, 6}) - result4 := Every([]int{0, 1, 2, 3, 4, 5}, []int{}) - - is.True(result1) - is.False(result2) - is.False(result3) - is.True(result4) -} - -func TestEveryBy(t *testing.T) { - t.Parallel() - is := assert.New(t) - - result1 := EveryBy([]int{1, 2, 3, 4}, func(x int) bool { - return x < 5 - }) - - is.True(result1) - - result2 := EveryBy([]int{1, 2, 3, 4}, func(x int) bool { - return x < 3 - }) - - is.False(result2) - - result3 := EveryBy([]int{1, 2, 3, 4}, func(x int) bool { - return x < 0 - }) - - is.False(result3) - - result4 := EveryBy([]int{}, func(x int) bool { - return x < 5 - }) - - is.True(result4) -} - -func TestSome(t *testing.T) { - t.Parallel() - is := assert.New(t) - - result1 := Some([]int{0, 1, 2, 3, 4, 5}, []int{0, 2}) - result2 := Some([]int{0, 1, 2, 3, 4, 5}, []int{0, 6}) - result3 := Some([]int{0, 1, 2, 3, 4, 5}, []int{-1, 6}) - result4 := Some([]int{0, 1, 2, 3, 4, 5}, []int{}) - - is.True(result1) - is.True(result2) - is.False(result3) - is.False(result4) -} - -func TestSomeBy(t *testing.T) { - t.Parallel() - is := assert.New(t) - - result1 := SomeBy([]int{1, 2, 3, 4}, func(x int) bool { - return x < 5 - }) - - is.True(result1) - - result2 := SomeBy([]int{1, 2, 3, 4}, func(x int) bool { - return x < 3 - }) - - is.True(result2) - - result3 := SomeBy([]int{1, 2, 3, 4}, func(x int) bool { - return x < 0 - }) - - is.False(result3) - - result4 := SomeBy([]int{}, func(x int) bool { - return x < 5 - }) - - is.False(result4) -} - -func TestNone(t *testing.T) { - t.Parallel() - is := assert.New(t) - - result1 := None([]int{0, 1, 2, 3, 4, 5}, []int{0, 2}) - result2 := None([]int{0, 1, 2, 3, 4, 5}, []int{0, 6}) - result3 := None([]int{0, 1, 2, 3, 4, 5}, []int{-1, 6}) - result4 := None([]int{0, 1, 2, 3, 4, 5}, []int{}) - - is.False(result1) - is.False(result2) - is.True(result3) - is.True(result4) -} - -func TestNoneBy(t *testing.T) { - t.Parallel() - is := assert.New(t) - - result1 := NoneBy([]int{1, 2, 3, 4}, func(x int) bool { - return x < 5 - }) - - is.False(result1) - - result2 := NoneBy([]int{1, 2, 3, 4}, func(x int) bool { - return x < 3 - }) - - is.False(result2) - - result3 := NoneBy([]int{1, 2, 3, 4}, func(x int) bool { - return x < 0 - }) - - is.True(result3) - - result4 := NoneBy([]int{}, func(x int) bool { - return x < 5 - }) - - is.True(result4) -} - -func TestIntersect(t *testing.T) { - t.Parallel() - is := assert.New(t) - - result1 := Intersect([]int{0, 1, 2, 3, 4, 5}, []int{0, 2}) - result2 := Intersect([]int{0, 1, 2, 3, 4, 5}, []int{0, 6}) - result3 := Intersect([]int{0, 1, 2, 3, 4, 5}, []int{-1, 6}) - result4 := Intersect([]int{0, 6}, []int{0, 1, 2, 3, 4, 5}) - result5 := Intersect([]int{0, 6, 0}, []int{0, 1, 2, 3, 4, 5}) - - is.Equal(result1, []int{0, 2}) - is.Equal(result2, []int{0}) - is.Equal(result3, []int{}) - is.Equal(result4, []int{0}) - is.Equal(result5, []int{0}) -} - -func TestDifference(t *testing.T) { - t.Parallel() - is := assert.New(t) - - left1, right1 := Difference([]int{0, 1, 2, 3, 4, 5}, []int{0, 2, 6}) - is.Equal(left1, []int{1, 3, 4, 5}) - is.Equal(right1, []int{6}) - - left2, right2 := Difference([]int{1, 2, 3, 4, 5}, []int{0, 6}) - is.Equal(left2, []int{1, 2, 3, 4, 5}) - is.Equal(right2, []int{0, 6}) - - left3, right3 := Difference([]int{0, 1, 2, 3, 4, 5}, []int{0, 1, 2, 3, 4, 5}) - is.Equal(left3, []int{}) - is.Equal(right3, []int{}) -} - -func TestUnion(t *testing.T) { - t.Parallel() - is := assert.New(t) - - result1 := Union([]int{0, 1, 2, 3, 4, 5}, []int{0, 2, 10}) - result2 := Union([]int{0, 1, 2, 3, 4, 5}, []int{6, 7}) - result3 := Union([]int{0, 1, 2, 3, 4, 5}, []int{}) - result4 := Union([]int{0, 1, 2}, []int{0, 1, 2}) - result5 := Union([]int{}, []int{}) - is.Equal(result1, []int{0, 1, 2, 3, 4, 5, 10}) - is.Equal(result2, []int{0, 1, 2, 3, 4, 5, 6, 7}) - is.Equal(result3, []int{0, 1, 2, 3, 4, 5}) - is.Equal(result4, []int{0, 1, 2}) - is.Equal(result5, []int{}) - - result11 := Union([]int{0, 1, 2, 3, 4, 5}, []int{0, 2, 10}, []int{0, 1, 11}) - result12 := Union([]int{0, 1, 2, 3, 4, 5}, []int{6, 7}, []int{8, 9}) - result13 := Union([]int{0, 1, 2, 3, 4, 5}, []int{}, []int{}) - result14 := Union([]int{0, 1, 2}, []int{0, 1, 2}, []int{0, 1, 2}) - result15 := Union([]int{}, []int{}, []int{}) - is.Equal(result11, []int{0, 1, 2, 3, 4, 5, 10, 11}) - is.Equal(result12, []int{0, 1, 2, 3, 4, 5, 6, 7, 8, 9}) - is.Equal(result13, []int{0, 1, 2, 3, 4, 5}) - is.Equal(result14, []int{0, 1, 2}) - is.Equal(result15, []int{}) -} - -func TestWithout(t *testing.T) { - t.Parallel() - is := assert.New(t) - - result1 := Without([]int{0, 2, 10}, 0, 1, 2, 3, 4, 5) - result2 := Without([]int{0, 7}, 0, 1, 2, 3, 4, 5) - result3 := Without([]int{}, 0, 1, 2, 3, 4, 5) - result4 := Without([]int{0, 1, 2}, 0, 1, 2) - result5 := Without([]int{}) - is.Equal(result1, []int{10}) - is.Equal(result2, []int{7}) - is.Equal(result3, []int{}) - is.Equal(result4, []int{}) - is.Equal(result5, []int{}) -} - -func TestWithoutEmpty(t *testing.T) { - t.Parallel() - is := assert.New(t) - - result1 := WithoutEmpty([]int{0, 1, 2}) - result2 := WithoutEmpty([]int{1, 2}) - result3 := WithoutEmpty([]int{}) - is.Equal(result1, []int{1, 2}) - is.Equal(result2, []int{1, 2}) - is.Equal(result3, []int{}) -} diff --git a/lo_test.go b/lo_test.go deleted file mode 100644 index 26db4c25..00000000 --- a/lo_test.go +++ /dev/null @@ -1,32 +0,0 @@ -package lo - -import ( - "os" - "testing" - "time" -) - -// https://github.com/stretchr/testify/issues/1101 -func testWithTimeout(t *testing.T, timeout time.Duration) { - t.Helper() - - testFinished := make(chan struct{}) - t.Cleanup(func() { close(testFinished) }) - - go func() { - select { - case <-testFinished: - case <-time.After(timeout): - t.Errorf("test timed out after %s", timeout) - os.Exit(1) - } - }() -} - -type foo struct { - bar string -} - -func (f foo) Clone() foo { - return foo{f.bar} -} diff --git a/map_example_test.go b/map_example_test.go deleted file mode 100644 index aebca8fd..00000000 --- a/map_example_test.go +++ /dev/null @@ -1,192 +0,0 @@ -package lo - -import ( - "fmt" - "sort" - "strconv" - "strings" -) - -func ExampleKeys() { - kv := map[string]int{"foo": 1, "bar": 2} - - result := Keys(kv) - - sort.StringSlice(result).Sort() - fmt.Printf("%v", result) - // Output: [bar foo] -} - -func ExampleValues() { - kv := map[string]int{"foo": 1, "bar": 2} - - result := Values(kv) - - sort.IntSlice(result).Sort() - fmt.Printf("%v", result) - // Output: [1 2] -} - -func ExampleValueOr() { - kv := map[string]int{"foo": 1, "bar": 2} - - result1 := ValueOr(kv, "foo", 42) - result2 := ValueOr(kv, "baz", 42) - - fmt.Printf("%v %v", result1, result2) - // Output: 1 42 -} - -func ExamplePickBy() { - kv := map[string]int{"foo": 1, "bar": 2, "baz": 3} - - result := PickBy(kv, func(key string, value int) bool { - return value%2 == 1 - }) - - fmt.Printf("%v %v %v", len(result), result["foo"], result["baz"]) - // Output: 2 1 3 -} - -func ExamplePickByKeys() { - kv := map[string]int{"foo": 1, "bar": 2, "baz": 3} - - result := PickByKeys(kv, []string{"foo", "baz"}) - - fmt.Printf("%v %v %v", len(result), result["foo"], result["baz"]) - // Output: 2 1 3 -} - -func ExamplePickByValues() { - kv := map[string]int{"foo": 1, "bar": 2, "baz": 3} - - result := PickByValues(kv, []int{1, 3}) - - fmt.Printf("%v %v %v", len(result), result["foo"], result["baz"]) - // Output: 2 1 3 -} - -func ExampleOmitBy() { - kv := map[string]int{"foo": 1, "bar": 2, "baz": 3} - - result := OmitBy(kv, func(key string, value int) bool { - return value%2 == 1 - }) - - fmt.Printf("%v", result) - // Output: map[bar:2] -} - -func ExampleOmitByKeys() { - kv := map[string]int{"foo": 1, "bar": 2, "baz": 3} - - result := OmitByKeys(kv, []string{"foo", "baz"}) - - fmt.Printf("%v", result) - // Output: map[bar:2] -} - -func ExampleOmitByValues() { - kv := map[string]int{"foo": 1, "bar": 2, "baz": 3} - - result := OmitByValues(kv, []int{1, 3}) - - fmt.Printf("%v", result) - // Output: map[bar:2] -} - -func ExampleEntries() { - kv := map[string]int{"foo": 1, "bar": 2, "baz": 3} - - result := Entries(kv) - - sort.Slice(result, func(i, j int) bool { - return strings.Compare(result[i].Key, result[j].Key) < 0 - }) - fmt.Printf("%v", result) - // Output: [{bar 2} {baz 3} {foo 1}] -} - -func ExampleFromEntries() { - result := FromEntries([]Entry[string, int]{ - { - Key: "foo", - Value: 1, - }, - { - Key: "bar", - Value: 2, - }, - { - Key: "baz", - Value: 3, - }, - }) - - fmt.Printf("%v %v %v %v", len(result), result["foo"], result["bar"], result["baz"]) - // Output: 3 1 2 3 -} - -func ExampleInvert() { - kv := map[string]int{"foo": 1, "bar": 2, "baz": 3} - - result := Invert(kv) - - fmt.Printf("%v %v %v %v", len(result), result[1], result[2], result[3]) - // Output: 3 foo bar baz -} - -func ExampleAssign() { - result := Assign( - map[string]int{"a": 1, "b": 2}, - map[string]int{"b": 3, "c": 4}, - ) - - fmt.Printf("%v %v %v %v", len(result), result["a"], result["b"], result["c"]) - // Output: 3 1 3 4 -} - -func ExampleMapKeys() { - kv := map[int]int{1: 1, 2: 2, 3: 3, 4: 4} - - result := MapKeys(kv, func(_ int, v int) string { - return strconv.FormatInt(int64(v), 10) - }) - - fmt.Printf("%v %v %v %v %v", len(result), result["1"], result["2"], result["3"], result["4"]) - // Output: 4 1 2 3 4 -} - -func ExampleMapValues() { - kv := map[int]int{1: 1, 2: 2, 3: 3, 4: 4} - - result := MapValues(kv, func(_ int, v int) string { - return strconv.FormatInt(int64(v), 10) - }) - - fmt.Printf("%v %v %v %v %v", len(result), result[1], result[2], result[3], result[4]) - // Output: 4 1 2 3 4 -} - -func ExampleMapEntries() { - kv := map[string]int{"foo": 1, "bar": 2} - - result := MapEntries(kv, func(k string, v int) (int, string) { - return v, k - }) - - fmt.Printf("%v\n", result) - // Output: map[1:foo 2:bar] -} - -func ExampleMapToSlice() { - kv := map[int]int64{1: 1, 2: 2, 3: 3, 4: 4} - - result := MapToSlice(kv, func(k int, v int64) string { - return fmt.Sprintf("%d_%d", k, v) - }) - - sort.StringSlice(result).Sort() - fmt.Printf("%v", result) - // Output: [1_1 2_2 3_3 4_4] -} diff --git a/map_test.go b/map_test.go deleted file mode 100644 index 419ca9fb..00000000 --- a/map_test.go +++ /dev/null @@ -1,337 +0,0 @@ -package lo - -import ( - "fmt" - "sort" - "strconv" - "testing" - - "github.com/stretchr/testify/assert" -) - -func TestKeys(t *testing.T) { - t.Parallel() - is := assert.New(t) - - r1 := Keys(map[string]int{"foo": 1, "bar": 2}) - sort.Strings(r1) - - is.Equal(r1, []string{"bar", "foo"}) -} - -func TestValues(t *testing.T) { - t.Parallel() - is := assert.New(t) - - r1 := Values(map[string]int{"foo": 1, "bar": 2}) - sort.Ints(r1) - - is.Equal(r1, []int{1, 2}) -} - -func TestValueOr(t *testing.T) { - t.Parallel() - is := assert.New(t) - - r1 := ValueOr(map[string]int{"foo": 1}, "bar", 2) - is.Equal(r1, 2) - - r2 := ValueOr(map[string]int{"foo": 1}, "foo", 2) - is.Equal(r2, 1) -} - -func TestPickBy(t *testing.T) { - t.Parallel() - is := assert.New(t) - - r1 := PickBy(map[string]int{"foo": 1, "bar": 2, "baz": 3}, func(key string, value int) bool { - return value%2 == 1 - }) - - is.Equal(r1, map[string]int{"foo": 1, "baz": 3}) -} - -func TestPickByKeys(t *testing.T) { - t.Parallel() - is := assert.New(t) - - r1 := PickByKeys(map[string]int{"foo": 1, "bar": 2, "baz": 3}, []string{"foo", "baz"}) - - is.Equal(r1, map[string]int{"foo": 1, "baz": 3}) -} - -func TestPickByValues(t *testing.T) { - t.Parallel() - is := assert.New(t) - - r1 := PickByValues(map[string]int{"foo": 1, "bar": 2, "baz": 3}, []int{1, 3}) - - is.Equal(r1, map[string]int{"foo": 1, "baz": 3}) -} - -func TestOmitBy(t *testing.T) { - t.Parallel() - is := assert.New(t) - - r1 := OmitBy(map[string]int{"foo": 1, "bar": 2, "baz": 3}, func(key string, value int) bool { - return value%2 == 1 - }) - - is.Equal(r1, map[string]int{"bar": 2}) -} - -func TestOmitByKeys(t *testing.T) { - t.Parallel() - is := assert.New(t) - - r1 := OmitByKeys(map[string]int{"foo": 1, "bar": 2, "baz": 3}, []string{"foo", "baz"}) - - is.Equal(r1, map[string]int{"bar": 2}) -} - -func TestOmitByValues(t *testing.T) { - t.Parallel() - is := assert.New(t) - - r1 := OmitByValues(map[string]int{"foo": 1, "bar": 2, "baz": 3}, []int{1, 3}) - - is.Equal(r1, map[string]int{"bar": 2}) -} - -func TestEntries(t *testing.T) { - t.Parallel() - is := assert.New(t) - - r1 := Entries(map[string]int{"foo": 1, "bar": 2}) - - sort.Slice(r1, func(i, j int) bool { - return r1[i].Value < r1[j].Value - }) - is.EqualValues(r1, []Entry[string, int]{ - { - Key: "foo", - Value: 1, - }, - { - Key: "bar", - Value: 2, - }, - }) -} - -func TestToPairs(t *testing.T) { - t.Parallel() - is := assert.New(t) - - r1 := ToPairs(map[string]int{"baz": 3, "qux": 4}) - - sort.Slice(r1, func(i, j int) bool { - return r1[i].Value < r1[j].Value - }) - is.EqualValues(r1, []Entry[string, int]{ - { - Key: "baz", - Value: 3, - }, - { - Key: "qux", - Value: 4, - }, - }) -} - -func TestFromEntries(t *testing.T) { - t.Parallel() - is := assert.New(t) - - r1 := FromEntries([]Entry[string, int]{ - { - Key: "foo", - Value: 1, - }, - { - Key: "bar", - Value: 2, - }, - }) - - is.Len(r1, 2) - is.Equal(r1["foo"], 1) - is.Equal(r1["bar"], 2) -} - -func TestFromPairs(t *testing.T) { - t.Parallel() - is := assert.New(t) - - r1 := FromPairs([]Entry[string, int]{ - { - Key: "baz", - Value: 3, - }, - { - Key: "qux", - Value: 4, - }, - }) - - is.Len(r1, 2) - is.Equal(r1["baz"], 3) - is.Equal(r1["qux"], 4) -} - -func TestInvert(t *testing.T) { - t.Parallel() - is := assert.New(t) - - r1 := Invert(map[string]int{"a": 1, "b": 2}) - r2 := Invert(map[string]int{"a": 1, "b": 2, "c": 1}) - - is.Len(r1, 2) - is.EqualValues(map[int]string{1: "a", 2: "b"}, r1) - is.Len(r2, 2) -} - -func TestAssign(t *testing.T) { - t.Parallel() - is := assert.New(t) - - result1 := Assign(map[string]int{"a": 1, "b": 2}, map[string]int{"b": 3, "c": 4}) - - is.Len(result1, 3) - is.Equal(result1, map[string]int{"a": 1, "b": 3, "c": 4}) -} - -func TestMapKeys(t *testing.T) { - t.Parallel() - is := assert.New(t) - - result1 := MapKeys(map[int]int{1: 1, 2: 2, 3: 3, 4: 4}, func(x int, _ int) string { - return "Hello" - }) - result2 := MapKeys(map[int]int{1: 1, 2: 2, 3: 3, 4: 4}, func(_ int, v int) string { - return strconv.FormatInt(int64(v), 10) - }) - - is.Equal(len(result1), 1) - is.Equal(len(result2), 4) - is.Equal(result2, map[string]int{"1": 1, "2": 2, "3": 3, "4": 4}) -} - -func TestMapValues(t *testing.T) { - t.Parallel() - is := assert.New(t) - - result1 := MapValues(map[int]int{1: 1, 2: 2, 3: 3, 4: 4}, func(x int, _ int) string { - return "Hello" - }) - result2 := MapValues(map[int]int{1: 1, 2: 2, 3: 3, 4: 4}, func(x int, _ int) string { - return strconv.FormatInt(int64(x), 10) - }) - - is.Equal(len(result1), 4) - is.Equal(len(result2), 4) - is.Equal(result1, map[int]string{1: "Hello", 2: "Hello", 3: "Hello", 4: "Hello"}) - is.Equal(result2, map[int]string{1: "1", 2: "2", 3: "3", 4: "4"}) -} - -func mapEntriesTest[I any, O any](t *testing.T, in map[string]I, iteratee func(string, I) (string, O), expected map[string]O) { - is := assert.New(t) - result := MapEntries(in, iteratee) - is.Equal(result, expected) -} - -func TestMapEntries(t *testing.T) { - mapEntriesTest(t, map[string]int{"foo": 1, "bar": 2}, func(k string, v int) (string, int) { - return k, v + 1 - }, map[string]int{"foo": 2, "bar": 3}) - mapEntriesTest(t, map[string]int{"foo": 1, "bar": 2}, func(k string, v int) (string, string) { - return k, k + strconv.Itoa(v) - }, map[string]string{"foo": "foo1", "bar": "bar2"}) - mapEntriesTest(t, map[string]int{"foo": 1, "bar": 2}, func(k string, v int) (string, string) { - return k, strconv.Itoa(v) + k - }, map[string]string{"foo": "1foo", "bar": "2bar"}) - - // NoMutation - { - is := assert.New(t) - r1 := map[string]int{"foo": 1, "bar": 2} - MapEntries(r1, func(k string, v int) (string, string) { - return k, strconv.Itoa(v) + "!!" - }) - is.Equal(r1, map[string]int{"foo": 1, "bar": 2}) - } - // EmptyInput - { - mapEntriesTest(t, map[string]int{}, func(k string, v int) (string, string) { - return k, strconv.Itoa(v) + "!!" - }, map[string]string{}) - - mapEntriesTest(t, map[string]any{}, func(k string, v any) (string, any) { - return k, v - }, map[string]any{}) - } - // Identity - { - mapEntriesTest(t, map[string]int{"foo": 1, "bar": 2}, func(k string, v int) (string, int) { - return k, v - }, map[string]int{"foo": 1, "bar": 2}) - mapEntriesTest(t, map[string]any{"foo": 1, "bar": "2", "ccc": true}, func(k string, v any) (string, any) { - return k, v - }, map[string]any{"foo": 1, "bar": "2", "ccc": true}) - } - // ToConstantEntry - { - mapEntriesTest(t, map[string]any{"foo": 1, "bar": "2", "ccc": true}, func(k string, v any) (string, any) { - return "key", "value" - }, map[string]any{"key": "value"}) - mapEntriesTest(t, map[string]any{"foo": 1, "bar": "2", "ccc": true}, func(k string, v any) (string, any) { - return "b", 5 - }, map[string]any{"b": 5}) - } - - //// OverlappingKeys - //// because using range over map, the order is not guaranteed - //// this test is not deterministic - //{ - // mapEntriesTest(t, map[string]any{"foo": 1, "foo2": 2, "Foo": 2, "Foo2": "2", "bar": "2", "ccc": true}, func(k string, v any) (string, any) { - // return string(k[0]), v - // }, map[string]any{"F": "2", "b": "2", "c": true, "f": 2}) - // mapEntriesTest(t, map[string]string{"foo": "1", "foo2": "2", "Foo": "2", "Foo2": "2", "bar": "2", "ccc": "true"}, func(k string, v string) (string, string) { - // return v, k - // }, map[string]string{"1": "foo", "2": "bar", "true": "ccc"}) - //} - //NormalMappers - { - mapEntriesTest(t, map[string]string{"foo": "1", "foo2": "2", "Foo": "2", "Foo2": "2", "bar": "2", "ccc": "true"}, func(k string, v string) (string, string) { - return k, k + v - }, map[string]string{"Foo": "Foo2", "Foo2": "Foo22", "bar": "bar2", "ccc": "ccctrue", "foo": "foo1", "foo2": "foo22"}) - - mapEntriesTest(t, map[string]struct { - name string - age int - }{"1-11-1": {name: "foo", age: 1}, "2-22-2": {name: "bar", age: 2}}, func(k string, v struct { - name string - age int - }) (string, string) { - return v.name, k - }, map[string]string{"bar": "2-22-2", "foo": "1-11-1"}) - } -} - -func TestMapToSlice(t *testing.T) { - t.Parallel() - is := assert.New(t) - - result1 := MapToSlice(map[int]int{1: 5, 2: 6, 3: 7, 4: 8}, func(k int, v int) string { - return fmt.Sprintf("%d_%d", k, v) - }) - result2 := MapToSlice(map[int]int{1: 5, 2: 6, 3: 7, 4: 8}, func(k int, _ int) string { - return strconv.FormatInt(int64(k), 10) - }) - - is.Equal(len(result1), 4) - is.Equal(len(result2), 4) - is.ElementsMatch(result1, []string{"1_5", "2_6", "3_7", "4_8"}) - is.ElementsMatch(result2, []string{"1", "2", "3", "4"}) -} diff --git a/math_example_test.go b/math_example_test.go deleted file mode 100644 index 00c6d972..00000000 --- a/math_example_test.go +++ /dev/null @@ -1,68 +0,0 @@ -package lo - -import ( - "fmt" -) - -func ExampleRange() { - result1 := Range(4) - result2 := Range(-4) - result3 := RangeFrom(1, 5) - result4 := RangeFrom(1.0, 5) - result5 := RangeWithSteps(0, 20, 5) - result6 := RangeWithSteps[float32](-1.0, -4.0, -1.0) - result7 := RangeWithSteps(1, 4, -1) - result8 := Range(0) - - fmt.Printf("%v\n", result1) - fmt.Printf("%v\n", result2) - fmt.Printf("%v\n", result3) - fmt.Printf("%v\n", result4) - fmt.Printf("%v\n", result5) - fmt.Printf("%v\n", result6) - fmt.Printf("%v\n", result7) - fmt.Printf("%v\n", result8) - // Output: - // [0 1 2 3] - // [0 -1 -2 -3] - // [1 2 3 4 5] - // [1 2 3 4 5] - // [0 5 10 15] - // [-1 -2 -3] - // [] - // [] -} - -func ExampleClamp() { - result1 := Clamp(0, -10, 10) - result2 := Clamp(-42, -10, 10) - result3 := Clamp(42, -10, 10) - - fmt.Printf("%v\n", result1) - fmt.Printf("%v\n", result2) - fmt.Printf("%v\n", result3) - // Output: - // 0 - // -10 - // 10 -} - -func ExampleSum() { - list := []int{1, 2, 3, 4, 5} - - sum := Sum(list) - - fmt.Printf("%v", sum) - // Output: 15 -} - -func ExampleSumBy() { - list := []string{"foo", "bar"} - - result := SumBy(list, func(item string) int { - return len(item) - }) - - fmt.Printf("%v", result) - // Output: 6 -} diff --git a/math_test.go b/math_test.go deleted file mode 100644 index d0bab70f..00000000 --- a/math_test.go +++ /dev/null @@ -1,99 +0,0 @@ -package lo - -import ( - "testing" - - "github.com/stretchr/testify/assert" -) - -func TestRange(t *testing.T) { - t.Parallel() - is := assert.New(t) - - result1 := Range(4) - result2 := Range(-4) - result3 := Range(0) - is.Equal(result1, []int{0, 1, 2, 3}) - is.Equal(result2, []int{0, -1, -2, -3}) - is.Equal(result3, []int{}) -} - -func TestRangeFrom(t *testing.T) { - t.Parallel() - is := assert.New(t) - - result1 := RangeFrom(1, 5) - result2 := RangeFrom(-1, -5) - result3 := RangeFrom(10, 0) - result4 := RangeFrom(2.0, 3) - result5 := RangeFrom(-2.0, -3) - is.Equal(result1, []int{1, 2, 3, 4, 5}) - is.Equal(result2, []int{-1, -2, -3, -4, -5}) - is.Equal(result3, []int{}) - is.Equal(result4, []float64{2.0, 3.0, 4.0}) - is.Equal(result5, []float64{-2.0, -3.0, -4.0}) -} - -func TestRangeClose(t *testing.T) { - t.Parallel() - is := assert.New(t) - - result1 := RangeWithSteps(0, 20, 6) - result2 := RangeWithSteps(0, 3, -5) - result3 := RangeWithSteps(1, 1, 0) - result4 := RangeWithSteps(3, 2, 1) - result5 := RangeWithSteps(1.0, 4.0, 2.0) - result6 := RangeWithSteps[float32](-1.0, -4.0, -1.0) - is.Equal([]int{0, 6, 12, 18}, result1) - is.Equal([]int{}, result2) - is.Equal([]int{}, result3) - is.Equal([]int{}, result4) - is.Equal([]float64{1.0, 3.0}, result5) - is.Equal([]float32{-1.0, -2.0, -3.0}, result6) -} - -func TestClamp(t *testing.T) { - t.Parallel() - is := assert.New(t) - - result1 := Clamp(0, -10, 10) - result2 := Clamp(-42, -10, 10) - result3 := Clamp(42, -10, 10) - - is.Equal(result1, 0) - is.Equal(result2, -10) - is.Equal(result3, 10) -} - -func TestSum(t *testing.T) { - is := assert.New(t) - - result1 := Sum([]float32{2.3, 3.3, 4, 5.3}) - result2 := Sum([]int32{2, 3, 4, 5}) - result3 := Sum([]uint32{2, 3, 4, 5}) - result4 := Sum([]uint32{}) - result5 := Sum([]complex128{4_4, 2_2}) - - is.Equal(result1, float32(14.900001)) - is.Equal(result2, int32(14)) - is.Equal(result3, uint32(14)) - is.Equal(result4, uint32(0)) - is.Equal(result5, complex128(6_6)) -} - -func TestSumBy(t *testing.T) { - t.Parallel() - is := assert.New(t) - - result1 := SumBy([]float32{2.3, 3.3, 4, 5.3}, func(n float32) float32 { return n }) - result2 := SumBy([]int32{2, 3, 4, 5}, func(n int32) int32 { return n }) - result3 := SumBy([]uint32{2, 3, 4, 5}, func(n uint32) uint32 { return n }) - result4 := SumBy([]uint32{}, func(n uint32) uint32 { return n }) - result5 := SumBy([]complex128{4_4, 2_2}, func(n complex128) complex128 { return n }) - - is.Equal(result1, float32(14.900001)) - is.Equal(result2, int32(14)) - is.Equal(result3, uint32(14)) - is.Equal(result4, uint32(0)) - is.Equal(result5, complex128(6_6)) -} diff --git a/parallel/slice_test.go b/parallel/slice_test.go deleted file mode 100644 index 248b45da..00000000 --- a/parallel/slice_test.go +++ /dev/null @@ -1,100 +0,0 @@ -package parallel - -import ( - "sort" - "strconv" - "sync/atomic" - "testing" - - "github.com/stretchr/testify/assert" -) - -func TestMap(t *testing.T) { - is := assert.New(t) - - result1 := Map([]int{1, 2, 3, 4}, func(x int, _ int) string { - return "Hello" - }) - result2 := Map([]int64{1, 2, 3, 4}, func(x int64, _ int) string { - return strconv.FormatInt(x, 10) - }) - - is.Equal(len(result1), 4) - is.Equal(len(result2), 4) - is.Equal(result1, []string{"Hello", "Hello", "Hello", "Hello"}) - is.Equal(result2, []string{"1", "2", "3", "4"}) -} - -func TestForEach(t *testing.T) { - is := assert.New(t) - - var counter uint64 - collection := []int{1, 2, 3, 4} - ForEach(collection, func(x int, i int) { - atomic.AddUint64(&counter, 1) - }) - - is.Equal(uint64(4), atomic.LoadUint64(&counter)) -} - -func TestTimes(t *testing.T) { - is := assert.New(t) - - result1 := Times(3, func(i int) string { - return strconv.FormatInt(int64(i), 10) - }) - - is.Equal(len(result1), 3) - is.Equal(result1, []string{"0", "1", "2"}) -} - -func TestGroupBy(t *testing.T) { - is := assert.New(t) - - result1 := GroupBy([]int{0, 1, 2, 3, 4, 5}, func(i int) int { - return i % 3 - }) - - // order - for x := range result1 { - sort.Slice(result1[x], func(i, j int) bool { - return result1[x][i] < result1[x][j] - }) - } - - is.EqualValues(len(result1), 3) - is.EqualValues(result1, map[int][]int{ - 0: {0, 3}, - 1: {1, 4}, - 2: {2, 5}, - }) -} - -func TestPartitionBy(t *testing.T) { - is := assert.New(t) - - oddEven := func(x int) string { - if x < 0 { - return "negative" - } else if x%2 == 0 { - return "even" - } - return "odd" - } - - result1 := PartitionBy([]int{-2, -1, 0, 1, 2, 3, 4, 5}, oddEven) - result2 := PartitionBy([]int{}, oddEven) - - // order - sort.Slice(result1, func(i, j int) bool { - return result1[i][0] < result1[j][0] - }) - for x := range result1 { - sort.Slice(result1[x], func(i, j int) bool { - return result1[x][i] < result1[x][j] - }) - } - - is.ElementsMatch(result1, [][]int{{-2, -1}, {0, 2, 4}, {1, 3, 5}}) - is.Equal(result2, [][]int{}) -} diff --git a/retry_example_test.go b/retry_example_test.go deleted file mode 100644 index 3560c2f0..00000000 --- a/retry_example_test.go +++ /dev/null @@ -1,251 +0,0 @@ -//go:build !race -// +build !race - -package lo - -import ( - "fmt" - "sync" - "sync/atomic" - "time" -) - -func ExampleNewDebounce() { - i := int32(0) - calls := []int32{} - mu := sync.Mutex{} - - debounce, cancel := NewDebounce(time.Millisecond, func() { - mu.Lock() - defer mu.Unlock() - calls = append(calls, atomic.LoadInt32(&i)) - }) - - debounce() - atomic.AddInt32(&i, 1) - - time.Sleep(5 * time.Millisecond) - - debounce() - atomic.AddInt32(&i, 1) - debounce() - atomic.AddInt32(&i, 1) - debounce() - atomic.AddInt32(&i, 1) - - time.Sleep(5 * time.Millisecond) - - cancel() - - mu.Lock() - fmt.Printf("%v", calls) - mu.Unlock() - // Output: [1 4] -} - -func ExampleNewDebounceBy() { - calls := map[string][]int{} - mu := sync.Mutex{} - - debounce, cancel := NewDebounceBy(time.Millisecond, func(userID string, count int) { - mu.Lock() - defer mu.Unlock() - - if _, ok := calls[userID]; !ok { - calls[userID] = []int{} - } - - calls[userID] = append(calls[userID], count) - }) - - debounce("samuel") - debounce("john") - - time.Sleep(5 * time.Millisecond) - - debounce("john") - debounce("john") - debounce("samuel") - debounce("john") - - time.Sleep(5 * time.Millisecond) - - cancel("samuel") - cancel("john") - - mu.Lock() - fmt.Printf("samuel: %v\n", calls["samuel"]) - fmt.Printf("john: %v\n", calls["john"]) - mu.Unlock() - // Output: - // samuel: [1 1] - // john: [1 3] -} - -func ExampleAttempt() { - count1, err1 := Attempt(2, func(i int) error { - if i == 0 { - return fmt.Errorf("error") - } - - return nil - }) - - count2, err2 := Attempt(2, func(i int) error { - if i < 10 { - return fmt.Errorf("error") - } - - return nil - }) - - fmt.Printf("%v %v\n", count1, err1) - fmt.Printf("%v %v\n", count2, err2) - // Output: - // 2 - // 2 error -} - -func ExampleAttemptWithDelay() { - count1, time1, err1 := AttemptWithDelay(2, time.Millisecond, func(i int, _ time.Duration) error { - if i == 0 { - return fmt.Errorf("error") - } - - return nil - }) - - count2, time2, err2 := AttemptWithDelay(2, time.Millisecond, func(i int, _ time.Duration) error { - if i < 10 { - return fmt.Errorf("error") - } - - return nil - }) - - fmt.Printf("%v %v %v\n", count1, time1.Truncate(time.Millisecond), err1) - fmt.Printf("%v %v %v\n", count2, time2.Truncate(time.Millisecond), err2) - // Output: - // 2 1ms - // 2 1ms error -} - -func ExampleTransaction() { - transaction := NewTransaction[int](). - Then( - func(state int) (int, error) { - fmt.Println("step 1") - return state + 10, nil - }, - func(state int) int { - fmt.Println("rollback 1") - return state - 10 - }, - ). - Then( - func(state int) (int, error) { - fmt.Println("step 2") - return state + 15, nil - }, - func(state int) int { - fmt.Println("rollback 2") - return state - 15 - }, - ). - Then( - func(state int) (int, error) { - fmt.Println("step 3") - - if true { - return state, fmt.Errorf("error") - } - - return state + 42, nil - }, - func(state int) int { - fmt.Println("rollback 3") - return state - 42 - }, - ) - - _, _ = transaction.Process(-5) - - // Output: - // step 1 - // step 2 - // step 3 - // rollback 2 - // rollback 1 -} - -func ExampleTransaction_ok() { - transaction := NewTransaction[int](). - Then( - func(state int) (int, error) { - return state + 10, nil - }, - func(state int) int { - return state - 10 - }, - ). - Then( - func(state int) (int, error) { - return state + 15, nil - }, - func(state int) int { - return state - 15 - }, - ). - Then( - func(state int) (int, error) { - return state + 42, nil - }, - func(state int) int { - return state - 42 - }, - ) - - state, err := transaction.Process(-5) - - fmt.Println(state) - fmt.Println(err) - // Output: - // 62 - // -} - -func ExampleTransaction_error() { - transaction := NewTransaction[int](). - Then( - func(state int) (int, error) { - return state + 10, nil - }, - func(state int) int { - return state - 10 - }, - ). - Then( - func(state int) (int, error) { - return state, fmt.Errorf("error") - }, - func(state int) int { - return state - 15 - }, - ). - Then( - func(state int) (int, error) { - return state + 42, nil - }, - func(state int) int { - return state - 42 - }, - ) - - state, err := transaction.Process(-5) - - fmt.Println(state) - fmt.Println(err) - // Output: - // -5 - // error -} diff --git a/retry_test.go b/retry_test.go deleted file mode 100644 index 91ad651b..00000000 --- a/retry_test.go +++ /dev/null @@ -1,500 +0,0 @@ -package lo - -import ( - "fmt" - "sync" - "testing" - "time" - - "github.com/stretchr/testify/assert" -) - -func TestAttempt(t *testing.T) { - t.Parallel() - is := assert.New(t) - - err := fmt.Errorf("failed") - - iter1, err1 := Attempt(42, func(i int) error { - return nil - }) - iter2, err2 := Attempt(42, func(i int) error { - if i == 5 { - return nil - } - - return err - }) - iter3, err3 := Attempt(2, func(i int) error { - if i == 5 { - return nil - } - - return err - }) - iter4, err4 := Attempt(0, func(i int) error { - if i < 42 { - return err - } - - return nil - }) - - is.Equal(iter1, 1) - is.Equal(err1, nil) - is.Equal(iter2, 6) - is.Equal(err2, nil) - is.Equal(iter3, 2) - is.Equal(err3, err) - is.Equal(iter4, 43) - is.Equal(err4, nil) -} - -func TestAttemptWithDelay(t *testing.T) { - t.Parallel() - is := assert.New(t) - - err := fmt.Errorf("failed") - - iter1, dur1, err1 := AttemptWithDelay(42, 10*time.Millisecond, func(i int, d time.Duration) error { - return nil - }) - iter2, dur2, err2 := AttemptWithDelay(42, 10*time.Millisecond, func(i int, d time.Duration) error { - if i == 5 { - return nil - } - - return err - }) - iter3, dur3, err3 := AttemptWithDelay(2, 10*time.Millisecond, func(i int, d time.Duration) error { - if i == 5 { - return nil - } - - return err - }) - iter4, dur4, err4 := AttemptWithDelay(0, 10*time.Millisecond, func(i int, d time.Duration) error { - if i < 10 { - return err - } - - return nil - }) - - is.Equal(iter1, 1) - is.Greater(dur1, 0*time.Millisecond) - is.Less(dur1, 1*time.Millisecond) - is.Equal(err1, nil) - is.Equal(iter2, 6) - is.Greater(dur2, 50*time.Millisecond) - is.Less(dur2, 60*time.Millisecond) - is.Equal(err2, nil) - is.Equal(iter3, 2) - is.Greater(dur3, 10*time.Millisecond) - is.Less(dur3, 20*time.Millisecond) - is.Equal(err3, err) - is.Equal(iter4, 11) - is.Greater(dur4, 100*time.Millisecond) - is.Less(dur4, 115*time.Millisecond) - is.Equal(err4, nil) -} - -func TestAttemptWhile(t *testing.T) { - is := assert.New(t) - - err := fmt.Errorf("failed") - - iter1, err1 := AttemptWhile(42, func(i int) (error, bool) { - return nil, true - }) - - is.Equal(iter1, 1) - is.Nil(err1) - - iter2, err2 := AttemptWhile(42, func(i int) (error, bool) { - if i == 5 { - return nil, true - } - - return err, true - }) - - is.Equal(iter2, 6) - is.Nil(err2) - - iter3, err3 := AttemptWhile(2, func(i int) (error, bool) { - if i == 5 { - return nil, true - } - - return err, true - }) - - is.Equal(iter3, 2) - is.Equal(err3, err) - - iter4, err4 := AttemptWhile(0, func(i int) (error, bool) { - if i < 42 { - return err, true - } - - return nil, true - }) - - is.Equal(iter4, 43) - is.Nil(err4) - - iter5, err5 := AttemptWhile(0, func(i int) (error, bool) { - if i == 5 { - return nil, false - } - - return err, true - }) - - is.Equal(iter5, 6) - is.Nil(err5) - - iter6, err6 := AttemptWhile(0, func(i int) (error, bool) { - return nil, false - }) - - is.Equal(iter6, 1) - is.Nil(err6) - - iter7, err7 := AttemptWhile(42, func(i int) (error, bool) { - if i == 42 { - return nil, false - } - if i < 41 { - return err, true - } - - return nil, true - }) - - is.Equal(iter7, 42) - is.Nil(err7) -} - -func TestAttemptWhileWithDelay(t *testing.T) { - is := assert.New(t) - - err := fmt.Errorf("failed") - - iter1, dur1, err1 := AttemptWhileWithDelay(42, 10*time.Millisecond, func(i int, d time.Duration) (error, bool) { - return nil, true - }) - - is.Equal(iter1, 1) - is.Greater(dur1, 0*time.Millisecond) - is.Less(dur1, 1*time.Millisecond) - is.Nil(err1) - - iter2, dur2, err2 := AttemptWhileWithDelay(42, 10*time.Millisecond, func(i int, d time.Duration) (error, bool) { - if i == 5 { - return nil, true - } - - return err, true - }) - - is.Equal(iter2, 6) - is.Greater(dur2, 50*time.Millisecond) - is.Less(dur2, 60*time.Millisecond) - is.Nil(err2) - - iter3, dur3, err3 := AttemptWhileWithDelay(2, 10*time.Millisecond, func(i int, d time.Duration) (error, bool) { - if i == 5 { - return nil, true - } - - return err, true - }) - - is.Equal(iter3, 2) - is.Greater(dur3, 10*time.Millisecond) - is.Less(dur3, 20*time.Millisecond) - is.Equal(err3, err) - - iter4, dur4, err4 := AttemptWhileWithDelay(0, 10*time.Millisecond, func(i int, d time.Duration) (error, bool) { - if i < 10 { - return err, true - } - - return nil, true - }) - - is.Equal(iter4, 11) - is.Greater(dur4, 100*time.Millisecond) - is.Less(dur4, 115*time.Millisecond) - is.Nil(err4) - - iter5, dur5, err5 := AttemptWhileWithDelay(0, 10*time.Millisecond, func(i int, d time.Duration) (error, bool) { - if i == 5 { - return nil, false - } - - return err, true - }) - - is.Equal(iter5, 6) - is.Greater(dur5, 10*time.Millisecond) - is.Less(dur5, 115*time.Millisecond) - is.Nil(err5) - - iter6, dur6, err6 := AttemptWhileWithDelay(0, 10*time.Millisecond, func(i int, d time.Duration) (error, bool) { - return nil, false - }) - - is.Equal(iter6, 1) - is.Less(dur6, 10*time.Millisecond) - is.Less(dur6, 115*time.Millisecond) - is.Nil(err6) - - iter7, dur7, err7 := AttemptWhileWithDelay(42, 10*time.Millisecond, func(i int, d time.Duration) (error, bool) { - if i == 42 { - return nil, false - } - if i < 41 { - return err, true - } - - return nil, true - }) - - is.Equal(iter7, 42) - is.Less(dur7, 500*time.Millisecond) - is.Nil(err7) -} - -func TestDebounce(t *testing.T) { - t.Parallel() - - f1 := func() { - println("1. Called once after 10ms when func stopped invoking!") - } - f2 := func() { - println("2. Called once after 10ms when func stopped invoking!") - } - f3 := func() { - println("3. Called once after 10ms when func stopped invoking!") - } - - d1, _ := NewDebounce(10*time.Millisecond, f1) - - // execute 3 times - for i := 0; i < 3; i++ { - for j := 0; j < 10; j++ { - d1() - } - time.Sleep(20 * time.Millisecond) - } - - d2, _ := NewDebounce(10*time.Millisecond, f2) - - // execute once because it is always invoked and only last invoke is worked after 100ms - for i := 0; i < 3; i++ { - for j := 0; j < 5; j++ { - d2() - } - time.Sleep(5 * time.Millisecond) - } - - time.Sleep(10 * time.Millisecond) - - // execute once because it is canceled after 200ms. - d3, cancel := NewDebounce(10*time.Millisecond, f3) - for i := 0; i < 3; i++ { - for j := 0; j < 10; j++ { - d3() - } - time.Sleep(20 * time.Millisecond) - if i == 0 { - cancel() - } - } -} - -func TestDebounceBy(t *testing.T) { - t.Parallel() - is := assert.New(t) - - mu := sync.Mutex{} - output := map[int]int{0: 0, 1: 0, 2: 0} - - f1 := func(key int, count int) { - mu.Lock() - output[key] += count - mu.Unlock() - // fmt.Printf("[key=%d] 1. Called once after 10ms when func stopped invoking!\n", key) - } - f2 := func(key int, count int) { - mu.Lock() - output[key] += count - mu.Unlock() - // fmt.Printf("[key=%d] 2. Called once after 10ms when func stopped invoking!\n", key) - } - f3 := func(key int, count int) { - mu.Lock() - output[key] += count - mu.Unlock() - // fmt.Printf("[key=%d] 3. Called once after 10ms when func stopped invoking!\n", key) - } - - d1, _ := NewDebounceBy(10*time.Millisecond, f1) - - // execute 3 times - for i := 0; i < 3; i++ { - for j := 0; j < 10; j++ { - for k := 0; k < 3; k++ { - d1(k) - } - } - time.Sleep(20 * time.Millisecond) - } - - mu.Lock() - is.EqualValues(output[0], 30) - is.EqualValues(output[1], 30) - is.EqualValues(output[2], 30) - mu.Unlock() - - d2, _ := NewDebounceBy(10*time.Millisecond, f2) - - // execute once because it is always invoked and only last invoke is worked after 100ms - for i := 0; i < 3; i++ { - for j := 0; j < 5; j++ { - for k := 0; k < 3; k++ { - d2(k) - } - } - time.Sleep(5 * time.Millisecond) - } - - time.Sleep(10 * time.Millisecond) - - mu.Lock() - is.EqualValues(output[0], 45) - is.EqualValues(output[1], 45) - is.EqualValues(output[2], 45) - mu.Unlock() - - // execute once because it is canceled after 200ms. - d3, cancel := NewDebounceBy(10*time.Millisecond, f3) - for i := 0; i < 3; i++ { - for j := 0; j < 10; j++ { - for k := 0; k < 3; k++ { - d3(k) - } - } - - time.Sleep(20 * time.Millisecond) - if i == 0 { - for k := 0; k < 3; k++ { - cancel(k) - } - } - } - - mu.Lock() - is.EqualValues(output[0], 75) - is.EqualValues(output[1], 75) - is.EqualValues(output[2], 75) - mu.Unlock() -} - -func TestTransation(t *testing.T) { - is := assert.New(t) - - // no error - { - transaction := NewTransaction[int](). - Then( - func(state int) (int, error) { - return state + 100, nil - }, - func(state int) int { - return state - 100 - }, - ). - Then( - func(state int) (int, error) { - return state + 21, nil - }, - func(state int) int { - return state - 21 - }, - ) - - state, err := transaction.Process(21) - is.Equal(142, state) - is.Equal(nil, err) - } - - // with error - { - transaction := NewTransaction[int](). - Then( - func(state int) (int, error) { - return state + 100, nil - }, - func(state int) int { - return state - 100 - }, - ). - Then( - func(state int) (int, error) { - return state, assert.AnError - }, - func(state int) int { - return state - 21 - }, - ). - Then( - func(state int) (int, error) { - return state + 42, nil - }, - func(state int) int { - return state - 42 - }, - ) - - state, err := transaction.Process(21) - is.Equal(21, state) - is.Equal(assert.AnError, err) - } - - // with error + update value - { - transaction := NewTransaction[int](). - Then( - func(state int) (int, error) { - return state + 100, nil - }, - func(state int) int { - return state - 100 - }, - ). - Then( - func(state int) (int, error) { - return state + 21, assert.AnError - }, - func(state int) int { - return state - 21 - }, - ). - Then( - func(state int) (int, error) { - return state + 42, nil - }, - func(state int) int { - return state - 42 - }, - ) - - state, err := transaction.Process(21) - is.Equal(42, state) - is.Equal(assert.AnError, err) - } -} diff --git a/slice_benchmark_test.go b/slice_benchmark_test.go deleted file mode 100644 index 38911c08..00000000 --- a/slice_benchmark_test.go +++ /dev/null @@ -1,173 +0,0 @@ -package lo - -import ( - "fmt" - "math/rand" - "strconv" - "testing" -) - -var lengths = []int{10, 100, 1000} - -func BenchmarkChunk(b *testing.B) { - for _, n := range lengths { - strs := genSliceString(n) - b.Run(fmt.Sprintf("strings_%d", n), func(b *testing.B) { - for i := 0; i < b.N; i++ { - _ = Chunk(strs, 5) - } - }) - } - - for _, n := range lengths { - ints := genSliceInt(n) - b.Run(fmt.Sprintf("ints%d", n), func(b *testing.B) { - for i := 0; i < b.N; i++ { - _ = Chunk(ints, 5) - } - }) - } -} - -func genSliceString(n int) []string { - res := make([]string, 0, n) - for i := 0; i < n; i++ { - res = append(res, strconv.Itoa(rand.Intn(100_000))) - } - return res -} - -func genSliceInt(n int) []int { - res := make([]int, 0, n) - for i := 0; i < n; i++ { - res = append(res, rand.Intn(100_000)) - } - return res -} - -func BenchmarkFlatten(b *testing.B) { - for _, n := range lengths { - ints := make([][]int, 0, n) - for i := 0; i < n; i++ { - ints = append(ints, genSliceInt(n)) - } - b.Run(fmt.Sprintf("ints_%d", n), func(b *testing.B) { - for i := 0; i < b.N; i++ { - _ = Flatten(ints) - } - }) - } - - for _, n := range lengths { - strs := make([][]string, 0, n) - for i := 0; i < n; i++ { - strs = append(strs, genSliceString(n)) - } - b.Run(fmt.Sprintf("strings_%d", n), func(b *testing.B) { - for i := 0; i < b.N; i++ { - _ = Flatten(strs) - } - }) - } -} - -func BenchmarkDrop(b *testing.B) { - for _, n := range lengths { - strs := genSliceString(n) - b.Run(fmt.Sprintf("strings_%d", n), func(b *testing.B) { - for i := 0; i < b.N; i++ { - _ = Drop(strs, n/4) - } - }) - } - - for _, n := range lengths { - ints := genSliceInt(n) - b.Run(fmt.Sprintf("ints%d", n), func(b *testing.B) { - for i := 0; i < b.N; i++ { - _ = Drop(ints, n/4) - } - }) - } -} - -func BenchmarkDropRight(b *testing.B) { - for _, n := range lengths { - strs := genSliceString(n) - b.Run(fmt.Sprintf("strings_%d", n), func(b *testing.B) { - for i := 0; i < b.N; i++ { - _ = DropRight(strs, n/4) - } - }) - } - - for _, n := range lengths { - ints := genSliceInt(n) - b.Run(fmt.Sprintf("ints%d", n), func(b *testing.B) { - for i := 0; i < b.N; i++ { - _ = DropRight(ints, n/4) - } - }) - } -} - -func BenchmarkDropWhile(b *testing.B) { - for _, n := range lengths { - strs := genSliceString(n) - b.Run(fmt.Sprintf("strings_%d", n), func(b *testing.B) { - for i := 0; i < b.N; i++ { - _ = DropWhile(strs, func(v string) bool { return len(v) < 4 }) - } - }) - } - - for _, n := range lengths { - ints := genSliceInt(n) - b.Run(fmt.Sprintf("ints%d", n), func(b *testing.B) { - for i := 0; i < b.N; i++ { - _ = DropWhile(ints, func(v int) bool { return i < 10_000 }) - } - }) - } -} - -func BenchmarkDropRightWhile(b *testing.B) { - for _, n := range lengths { - strs := genSliceString(n) - b.Run(fmt.Sprintf("strings_%d", n), func(b *testing.B) { - for i := 0; i < b.N; i++ { - _ = DropRightWhile(strs, func(v string) bool { return len(v) < 4 }) - } - }) - } - - for _, n := range lengths { - ints := genSliceInt(n) - b.Run(fmt.Sprintf("ints%d", n), func(b *testing.B) { - for i := 0; i < b.N; i++ { - _ = DropRightWhile(ints, func(v int) bool { return i < 10_000 }) - } - }) - } -} - -func BenchmarkReplace(b *testing.B) { - lengths := []int{1_000, 10_000, 100_000} - for _, n := range lengths { - strs := genSliceString(n) - b.Run(fmt.Sprintf("strings_%d", n), func(b *testing.B) { - for i := 0; i < b.N; i++ { - _ = Replace(strs, strs[n/4], "123123", 10) - } - }) - } - - for _, n := range lengths { - ints := genSliceInt(n) - b.Run(fmt.Sprintf("ints%d", n), func(b *testing.B) { - for i := 0; i < b.N; i++ { - _ = Replace(ints, ints[n/4], 123123, 10) - } - }) - } -} diff --git a/slice_example_test.go b/slice_example_test.go deleted file mode 100644 index b5b49d2b..00000000 --- a/slice_example_test.go +++ /dev/null @@ -1,458 +0,0 @@ -package lo - -import ( - "fmt" - "math" - "strconv" -) - -func ExampleFilter() { - list := []int64{1, 2, 3, 4} - - result := Filter(list, func(nbr int64, index int) bool { - return nbr%2 == 0 - }) - - fmt.Printf("%v", result) - // Output: [2 4] -} - -func ExampleMap() { - list := []int64{1, 2, 3, 4} - - result := Map(list, func(nbr int64, index int) string { - return strconv.FormatInt(nbr*2, 10) - }) - - fmt.Printf("%v", result) - // Output: [2 4 6 8] -} - -func ExampleFilterMap() { - list := []int64{1, 2, 3, 4} - - result := FilterMap(list, func(nbr int64, index int) (string, bool) { - return strconv.FormatInt(nbr*2, 10), nbr%2 == 0 - }) - - fmt.Printf("%v", result) - // Output: [4 8] -} - -func ExampleFlatMap() { - list := []int64{1, 2, 3, 4} - - result := FlatMap(list, func(nbr int64, index int) []string { - return []string{ - strconv.FormatInt(nbr, 10), // base 10 - strconv.FormatInt(nbr, 2), // base 2 - } - }) - - fmt.Printf("%v", result) - // Output: [1 1 2 10 3 11 4 100] -} - -func ExampleReduce() { - list := []int64{1, 2, 3, 4} - - result := Reduce(list, func(agg int64, item int64, index int) int64 { - return agg + item - }, 0) - - fmt.Printf("%v", result) - // Output: 10 -} - -func ExampleReduceRight() { - list := [][]int{{0, 1}, {2, 3}, {4, 5}} - - result := ReduceRight(list, func(agg []int, item []int, index int) []int { - return append(agg, item...) - }, []int{}) - - fmt.Printf("%v", result) - // Output: [4 5 2 3 0 1] -} - -func ExampleForEach() { - list := []int64{1, 2, 3, 4} - - ForEach(list, func(x int64, _ int) { - fmt.Println(x) - }) - - // Output: - // 1 - // 2 - // 3 - // 4 -} - -func ExampleTimes() { - result := Times(3, func(i int) string { - return strconv.FormatInt(int64(i), 10) - }) - - fmt.Printf("%v", result) - // Output: [0 1 2] -} - -func ExampleUniq() { - list := []int{1, 2, 2, 1} - - result := Uniq(list) - - fmt.Printf("%v", result) - // Output: [1 2] -} - -func ExampleUniqBy() { - list := []int{0, 1, 2, 3, 4, 5} - - result := UniqBy(list, func(i int) int { - return i % 3 - }) - - fmt.Printf("%v", result) - // Output: [0 1 2] -} - -func ExampleGroupBy() { - list := []int{0, 1, 2, 3, 4, 5} - - result := GroupBy(list, func(i int) int { - return i % 3 - }) - - fmt.Printf("%v\n", result[0]) - fmt.Printf("%v\n", result[1]) - fmt.Printf("%v\n", result[2]) - // Output: - // [0 3] - // [1 4] - // [2 5] -} - -func ExampleChunk() { - list := []int{0, 1, 2, 3, 4} - - result := Chunk(list, 2) - - for _, item := range result { - fmt.Printf("%v\n", item) - } - // Output: - // [0 1] - // [2 3] - // [4] -} - -func ExamplePartitionBy() { - list := []int{-2, -1, 0, 1, 2, 3, 4} - - result := PartitionBy(list, func(x int) string { - if x < 0 { - return "negative" - } else if x%2 == 0 { - return "even" - } - return "odd" - }) - - for _, item := range result { - fmt.Printf("%v\n", item) - } - // Output: - // [-2 -1] - // [0 2 4] - // [1 3] -} - -func ExampleFlatten() { - list := [][]int{{0, 1, 2}, {3, 4, 5}} - - result := Flatten(list) - - fmt.Printf("%v", result) - // Output: [0 1 2 3 4 5] -} - -func ExampleInterleave() { - list1 := [][]int{{1, 4, 7}, {2, 5, 8}, {3, 6, 9}} - list2 := [][]int{{1}, {2, 5, 8}, {3, 6}, {4, 7, 9, 10}} - - result1 := Interleave(list1...) - result2 := Interleave(list2...) - - fmt.Printf("%v\n", result1) - fmt.Printf("%v\n", result2) - // Output: - // [1 2 3 4 5 6 7 8 9] - // [1 2 3 4 5 6 7 8 9 10] -} - -func ExampleShuffle() { - list := []int{0, 1, 2, 3, 4, 5} - - result := Shuffle(list) - - fmt.Printf("%v", result) -} - -func ExampleReverse() { - list := []int{0, 1, 2, 3, 4, 5} - - result := Reverse(list) - - fmt.Printf("%v", result) - // Output: [5 4 3 2 1 0] -} - -func ExampleFill() { - list := []foo{{"a"}, {"a"}} - - result := Fill(list, foo{"b"}) - - fmt.Printf("%v", result) - // Output: [{b} {b}] -} - -func ExampleRepeat() { - result := Repeat(2, foo{"a"}) - - fmt.Printf("%v", result) - // Output: [{a} {a}] -} - -func ExampleRepeatBy() { - result := RepeatBy(5, func(i int) string { - return strconv.FormatInt(int64(math.Pow(float64(i), 2)), 10) - }) - - fmt.Printf("%v", result) - // Output: [0 1 4 9 16] -} - -func ExampleKeyBy() { - list := []string{"a", "aa", "aaa"} - - result := KeyBy(list, func(str string) int { - return len(str) - }) - - fmt.Printf("%v", result) - // Output: map[1:a 2:aa 3:aaa] -} - -func ExampleAssociate() { - list := []string{"a", "aa", "aaa"} - - result := Associate(list, func(str string) (string, int) { - return str, len(str) - }) - - fmt.Printf("%v", result) - // Output: map[a:1 aa:2 aaa:3] -} - -func ExampleDrop() { - list := []int{0, 1, 2, 3, 4, 5} - - result := Drop(list, 2) - - fmt.Printf("%v", result) - // Output: [2 3 4 5] -} - -func ExampleDropRight() { - list := []int{0, 1, 2, 3, 4, 5} - - result := DropRight(list, 2) - - fmt.Printf("%v", result) - // Output: [0 1 2 3] -} - -func ExampleDropWhile() { - list := []int{0, 1, 2, 3, 4, 5} - - result := DropWhile(list, func(val int) bool { - return val < 2 - }) - - fmt.Printf("%v", result) - // Output: [2 3 4 5] -} - -func ExampleDropRightWhile() { - list := []int{0, 1, 2, 3, 4, 5} - - result := DropRightWhile(list, func(val int) bool { - return val > 2 - }) - - fmt.Printf("%v", result) - // Output: [0 1 2] -} - -func ExampleReject() { - list := []int{0, 1, 2, 3, 4, 5} - - result := Reject(list, func(x int, _ int) bool { - return x%2 == 0 - }) - - fmt.Printf("%v", result) - // Output: [1 3 5] -} - -func ExampleCount() { - list := []int{0, 1, 2, 3, 4, 5, 0, 1, 2, 3} - - result := Count(list, 2) - - fmt.Printf("%v", result) - // Output: 2 -} - -func ExampleCountBy() { - list := []int{0, 1, 2, 3, 4, 5, 0, 1, 2, 3} - - result := CountBy(list, func(i int) bool { - return i < 4 - }) - - fmt.Printf("%v", result) - // Output: 8 -} - -func ExampleCountValues() { - result1 := CountValues([]int{}) - result2 := CountValues([]int{1, 2}) - result3 := CountValues([]int{1, 2, 2}) - result4 := CountValues([]string{"foo", "bar", ""}) - result5 := CountValues([]string{"foo", "bar", "bar"}) - - fmt.Printf("%v\n", result1) - fmt.Printf("%v\n", result2) - fmt.Printf("%v\n", result3) - fmt.Printf("%v\n", result4) - fmt.Printf("%v\n", result5) - // Output: - // map[] - // map[1:1 2:1] - // map[1:1 2:2] - // map[:1 bar:1 foo:1] - // map[bar:2 foo:1] -} - -func ExampleCountValuesBy() { - isEven := func(v int) bool { - return v%2 == 0 - } - - result1 := CountValuesBy([]int{}, isEven) - result2 := CountValuesBy([]int{1, 2}, isEven) - result3 := CountValuesBy([]int{1, 2, 2}, isEven) - - length := func(v string) int { - return len(v) - } - - result4 := CountValuesBy([]string{"foo", "bar", ""}, length) - result5 := CountValuesBy([]string{"foo", "bar", "bar"}, length) - - fmt.Printf("%v\n", result1) - fmt.Printf("%v\n", result2) - fmt.Printf("%v\n", result3) - fmt.Printf("%v\n", result4) - fmt.Printf("%v\n", result5) - // Output: - // map[] - // map[false:1 true:1] - // map[false:1 true:2] - // map[0:1 3:2] - // map[3:3] -} - -func ExampleSubset() { - list := []int{0, 1, 2, 3, 4, 5} - - result := Subset(list, 2, 3) - - fmt.Printf("%v", result) - // Output: [2 3 4] -} - -func ExampleSlice() { - list := []int{0, 1, 2, 3, 4, 5} - - result := Slice(list, 1, 4) - fmt.Printf("%v\n", result) - - result = Slice(list, 4, 1) - fmt.Printf("%v\n", result) - - result = Slice(list, 4, 5) - fmt.Printf("%v\n", result) - - // Output: - // [1 2 3] - // [] - // [4] -} - -func ExampleReplace() { - list := []int{0, 1, 0, 1, 2, 3, 0} - - result := Replace(list, 0, 42, 1) - fmt.Printf("%v\n", result) - - result = Replace(list, -1, 42, 1) - fmt.Printf("%v\n", result) - - result = Replace(list, 0, 42, 2) - fmt.Printf("%v\n", result) - - result = Replace(list, 0, 42, -1) - fmt.Printf("%v\n", result) - - // Output: - // [42 1 0 1 2 3 0] - // [0 1 0 1 2 3 0] - // [42 1 42 1 2 3 0] - // [42 1 42 1 2 3 42] -} - -func ExampleReplaceAll() { - list := []string{"", "foo", "", "bar", ""} - - result := Compact(list) - - fmt.Printf("%v", result) - - // Output: [foo bar] -} - -func ExampleIsSorted() { - list := []int{0, 1, 2, 3, 4, 5, 6, 7, 8, 9} - - result := IsSorted(list) - - fmt.Printf("%v", result) - - // Output: true -} - -func ExampleIsSortedByKey() { - list := []string{"a", "bb", "ccc"} - - result := IsSortedByKey(list, func(s string) int { - return len(s) - }) - - fmt.Printf("%v", result) - - // Output: true -} diff --git a/slice_test.go b/slice_test.go deleted file mode 100644 index 03326a01..00000000 --- a/slice_test.go +++ /dev/null @@ -1,761 +0,0 @@ -package lo - -import ( - "fmt" - "math" - "reflect" - "strconv" - "strings" - "testing" - - "github.com/stretchr/testify/assert" -) - -func TestFilter(t *testing.T) { - t.Parallel() - is := assert.New(t) - - r1 := Filter([]int{1, 2, 3, 4}, func(x int, _ int) bool { - return x%2 == 0 - }) - - is.Equal(r1, []int{2, 4}) - - r2 := Filter([]string{"", "foo", "", "bar", ""}, func(x string, _ int) bool { - return len(x) > 0 - }) - - is.Equal(r2, []string{"foo", "bar"}) -} - -func TestMap(t *testing.T) { - t.Parallel() - is := assert.New(t) - - result1 := Map([]int{1, 2, 3, 4}, func(x int, _ int) string { - return "Hello" - }) - result2 := Map([]int64{1, 2, 3, 4}, func(x int64, _ int) string { - return strconv.FormatInt(x, 10) - }) - - is.Equal(len(result1), 4) - is.Equal(len(result2), 4) - is.Equal(result1, []string{"Hello", "Hello", "Hello", "Hello"}) - is.Equal(result2, []string{"1", "2", "3", "4"}) -} - -func TestFilterMap(t *testing.T) { - t.Parallel() - is := assert.New(t) - - r1 := FilterMap([]int64{1, 2, 3, 4}, func(x int64, _ int) (string, bool) { - if x%2 == 0 { - return strconv.FormatInt(x, 10), true - } - return "", false - }) - r2 := FilterMap([]string{"cpu", "gpu", "mouse", "keyboard"}, func(x string, _ int) (string, bool) { - if strings.HasSuffix(x, "pu") { - return "xpu", true - } - return "", false - }) - - is.Equal(len(r1), 2) - is.Equal(len(r2), 2) - is.Equal(r1, []string{"2", "4"}) - is.Equal(r2, []string{"xpu", "xpu"}) -} - -func TestFlatMap(t *testing.T) { - t.Parallel() - is := assert.New(t) - - result1 := FlatMap([]int{0, 1, 2, 3, 4}, func(x int, _ int) []string { - return []string{"Hello"} - }) - result2 := FlatMap([]int64{0, 1, 2, 3, 4}, func(x int64, _ int) []string { - result := make([]string, 0, x) - for i := int64(0); i < x; i++ { - result = append(result, strconv.FormatInt(x, 10)) - } - return result - }) - - is.Equal(len(result1), 5) - is.Equal(len(result2), 10) - is.Equal(result1, []string{"Hello", "Hello", "Hello", "Hello", "Hello"}) - is.Equal(result2, []string{"1", "2", "2", "3", "3", "3", "4", "4", "4", "4"}) -} - -func TestTimes(t *testing.T) { - t.Parallel() - is := assert.New(t) - - result1 := Times(3, func(i int) string { - return strconv.FormatInt(int64(i), 10) - }) - - is.Equal(len(result1), 3) - is.Equal(result1, []string{"0", "1", "2"}) -} - -func TestReduce(t *testing.T) { - t.Parallel() - is := assert.New(t) - - result1 := Reduce([]int{1, 2, 3, 4}, func(agg int, item int, _ int) int { - return agg + item - }, 0) - result2 := Reduce([]int{1, 2, 3, 4}, func(agg int, item int, _ int) int { - return agg + item - }, 10) - - is.Equal(result1, 10) - is.Equal(result2, 20) -} - -func TestReduceRight(t *testing.T) { - t.Parallel() - is := assert.New(t) - - result1 := ReduceRight([][]int{{0, 1}, {2, 3}, {4, 5}}, func(agg []int, item []int, _ int) []int { - return append(agg, item...) - }, []int{}) - - is.Equal(result1, []int{4, 5, 2, 3, 0, 1}) -} - -func TestForEach(t *testing.T) { - t.Parallel() - is := assert.New(t) - - // check of callback is called for every element and in proper order - - callParams1 := []string{} - callParams2 := []int{} - - ForEach([]string{"a", "b", "c"}, func(item string, i int) { - callParams1 = append(callParams1, item) - callParams2 = append(callParams2, i) - }) - - is.ElementsMatch([]string{"a", "b", "c"}, callParams1) - is.ElementsMatch([]int{0, 1, 2}, callParams2) - is.IsIncreasing(callParams2) -} - -func TestUniq(t *testing.T) { - t.Parallel() - is := assert.New(t) - - result1 := Uniq([]int{1, 2, 2, 1}) - - is.Equal(len(result1), 2) - is.Equal(result1, []int{1, 2}) -} - -func TestUniqBy(t *testing.T) { - t.Parallel() - is := assert.New(t) - - result1 := UniqBy([]int{0, 1, 2, 3, 4, 5}, func(i int) int { - return i % 3 - }) - - is.Equal(len(result1), 3) - is.Equal(result1, []int{0, 1, 2}) -} - -func TestGroupBy(t *testing.T) { - t.Parallel() - is := assert.New(t) - - result1 := GroupBy([]int{0, 1, 2, 3, 4, 5}, func(i int) int { - return i % 3 - }) - - is.Equal(len(result1), 3) - is.Equal(result1, map[int][]int{ - 0: {0, 3}, - 1: {1, 4}, - 2: {2, 5}, - }) -} - -func TestChunk(t *testing.T) { - t.Parallel() - is := assert.New(t) - - result1 := Chunk([]int{0, 1, 2, 3, 4, 5}, 2) - result2 := Chunk([]int{0, 1, 2, 3, 4, 5, 6}, 2) - result3 := Chunk([]int{}, 2) - result4 := Chunk([]int{0}, 2) - - is.Equal(result1, [][]int{{0, 1}, {2, 3}, {4, 5}}) - is.Equal(result2, [][]int{{0, 1}, {2, 3}, {4, 5}, {6}}) - is.Equal(result3, [][]int{}) - is.Equal(result4, [][]int{{0}}) - is.PanicsWithValue("Second parameter must be greater than 0", func() { - Chunk([]int{0}, 0) - }) -} - -func TestPartitionBy(t *testing.T) { - t.Parallel() - is := assert.New(t) - - oddEven := func(x int) string { - if x < 0 { - return "negative" - } else if x%2 == 0 { - return "even" - } - return "odd" - } - - result1 := PartitionBy([]int{-2, -1, 0, 1, 2, 3, 4, 5}, oddEven) - result2 := PartitionBy([]int{}, oddEven) - - is.Equal(result1, [][]int{{-2, -1}, {0, 2, 4}, {1, 3, 5}}) - is.Equal(result2, [][]int{}) -} - -func TestFlatten(t *testing.T) { - t.Parallel() - is := assert.New(t) - - result1 := Flatten([][]int{{0, 1}, {2, 3, 4, 5}}) - - is.Equal(result1, []int{0, 1, 2, 3, 4, 5}) -} - -func TestInterleave(t *testing.T) { - tests := []struct { - name string - collections [][]int - want []int - }{ - { - "nil", - [][]int{nil}, - []int{}, - }, - { - "empty", - [][]int{}, - []int{}, - }, - { - "empties", - [][]int{{}, {}}, - []int{}, - }, - { - "same length", - [][]int{{1, 3, 5}, {2, 4, 6}}, - []int{1, 2, 3, 4, 5, 6}, - }, - { - "different length", - [][]int{{1, 3, 5, 6}, {2, 4}}, - []int{1, 2, 3, 4, 5, 6}, - }, - { - "many slices", - [][]int{{1}, {2, 5, 8}, {3, 6}, {4, 7, 9, 10}}, - []int{1, 2, 3, 4, 5, 6, 7, 8, 9, 10}, - }, - } - for _, tt := range tests { - t.Run(tt.name, func(t *testing.T) { - if got := Interleave(tt.collections...); !reflect.DeepEqual(got, tt.want) { - t.Errorf("Interleave() = %v, want %v", got, tt.want) - } - }) - } -} - -func TestShuffle(t *testing.T) { - t.Parallel() - is := assert.New(t) - - result1 := Shuffle([]int{0, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10}) - result2 := Shuffle([]int{}) - - is.NotEqual(result1, []int{0, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10}) - is.Equal(result2, []int{}) -} - -func TestReverse(t *testing.T) { - t.Parallel() - is := assert.New(t) - - result1 := Reverse([]int{0, 1, 2, 3, 4, 5}) - result2 := Reverse([]int{0, 1, 2, 3, 4, 5, 6}) - result3 := Reverse([]int{}) - - is.Equal(result1, []int{5, 4, 3, 2, 1, 0}) - is.Equal(result2, []int{6, 5, 4, 3, 2, 1, 0}) - is.Equal(result3, []int{}) -} - -func TestFill(t *testing.T) { - t.Parallel() - is := assert.New(t) - - result1 := Fill([]foo{{"a"}, {"a"}}, foo{"b"}) - result2 := Fill([]foo{}, foo{"a"}) - - is.Equal(result1, []foo{{"b"}, {"b"}}) - is.Equal(result2, []foo{}) -} - -func TestRepeat(t *testing.T) { - t.Parallel() - is := assert.New(t) - - result1 := Repeat(2, foo{"a"}) - result2 := Repeat(0, foo{"a"}) - - is.Equal(result1, []foo{{"a"}, {"a"}}) - is.Equal(result2, []foo{}) -} - -func TestRepeatBy(t *testing.T) { - t.Parallel() - is := assert.New(t) - - cb := func(i int) int { - return int(math.Pow(float64(i), 2)) - } - - result1 := RepeatBy(0, cb) - result2 := RepeatBy(2, cb) - result3 := RepeatBy(5, cb) - - is.Equal([]int{}, result1) - is.Equal([]int{0, 1}, result2) - is.Equal([]int{0, 1, 4, 9, 16}, result3) -} - -func TestKeyBy(t *testing.T) { - t.Parallel() - is := assert.New(t) - - result1 := KeyBy([]string{"a", "aa", "aaa"}, func(str string) int { - return len(str) - }) - - is.Equal(result1, map[int]string{1: "a", 2: "aa", 3: "aaa"}) -} - -func TestAssociate(t *testing.T) { - t.Parallel() - - type foo struct { - baz string - bar int - } - transform := func(f *foo) (string, int) { - return f.baz, f.bar - } - testCases := []struct { - in []*foo - expect map[string]int - }{ - { - in: []*foo{{baz: "apple", bar: 1}}, - expect: map[string]int{"apple": 1}, - }, - { - in: []*foo{{baz: "apple", bar: 1}, {baz: "banana", bar: 2}}, - expect: map[string]int{"apple": 1, "banana": 2}, - }, - { - in: []*foo{{baz: "apple", bar: 1}, {baz: "apple", bar: 2}}, - expect: map[string]int{"apple": 2}, - }, - } - for i, testCase := range testCases { - t.Run(fmt.Sprintf("test_%d", i), func(t *testing.T) { - is := assert.New(t) - is.Equal(Associate(testCase.in, transform), testCase.expect) - }) - } -} - -func TestSliceToMap(t *testing.T) { - t.Parallel() - - type foo struct { - baz string - bar int - } - transform := func(f *foo) (string, int) { - return f.baz, f.bar - } - testCases := []struct { - in []*foo - expect map[string]int - }{ - { - in: []*foo{{baz: "apple", bar: 1}}, - expect: map[string]int{"apple": 1}, - }, - { - in: []*foo{{baz: "apple", bar: 1}, {baz: "banana", bar: 2}}, - expect: map[string]int{"apple": 1, "banana": 2}, - }, - { - in: []*foo{{baz: "apple", bar: 1}, {baz: "apple", bar: 2}}, - expect: map[string]int{"apple": 2}, - }, - } - for i, testCase := range testCases { - t.Run(fmt.Sprintf("test_%d", i), func(t *testing.T) { - is := assert.New(t) - is.Equal(SliceToMap(testCase.in, transform), testCase.expect) - }) - } -} - -func TestDrop(t *testing.T) { - t.Parallel() - is := assert.New(t) - - is.Equal([]int{1, 2, 3, 4}, Drop([]int{0, 1, 2, 3, 4}, 1)) - is.Equal([]int{2, 3, 4}, Drop([]int{0, 1, 2, 3, 4}, 2)) - is.Equal([]int{3, 4}, Drop([]int{0, 1, 2, 3, 4}, 3)) - is.Equal([]int{4}, Drop([]int{0, 1, 2, 3, 4}, 4)) - is.Equal([]int{}, Drop([]int{0, 1, 2, 3, 4}, 5)) - is.Equal([]int{}, Drop([]int{0, 1, 2, 3, 4}, 6)) -} - -func TestDropRight(t *testing.T) { - t.Parallel() - is := assert.New(t) - - is.Equal([]int{0, 1, 2, 3}, DropRight([]int{0, 1, 2, 3, 4}, 1)) - is.Equal([]int{0, 1, 2}, DropRight([]int{0, 1, 2, 3, 4}, 2)) - is.Equal([]int{0, 1}, DropRight([]int{0, 1, 2, 3, 4}, 3)) - is.Equal([]int{0}, DropRight([]int{0, 1, 2, 3, 4}, 4)) - is.Equal([]int{}, DropRight([]int{0, 1, 2, 3, 4}, 5)) - is.Equal([]int{}, DropRight([]int{0, 1, 2, 3, 4}, 6)) -} - -func TestDropWhile(t *testing.T) { - t.Parallel() - is := assert.New(t) - - is.Equal([]int{4, 5, 6}, DropWhile([]int{0, 1, 2, 3, 4, 5, 6}, func(t int) bool { - return t != 4 - })) - - is.Equal([]int{}, DropWhile([]int{0, 1, 2, 3, 4, 5, 6}, func(t int) bool { - return true - })) - - is.Equal([]int{0, 1, 2, 3, 4, 5, 6}, DropWhile([]int{0, 1, 2, 3, 4, 5, 6}, func(t int) bool { - return t == 10 - })) -} - -func TestDropRightWhile(t *testing.T) { - t.Parallel() - is := assert.New(t) - - is.Equal([]int{0, 1, 2, 3}, DropRightWhile([]int{0, 1, 2, 3, 4, 5, 6}, func(t int) bool { - return t != 3 - })) - - is.Equal([]int{0, 1}, DropRightWhile([]int{0, 1, 2, 3, 4, 5, 6}, func(t int) bool { - return t != 1 - })) - - is.Equal([]int{0, 1, 2, 3, 4, 5, 6}, DropRightWhile([]int{0, 1, 2, 3, 4, 5, 6}, func(t int) bool { - return t == 10 - })) - - is.Equal([]int{}, DropRightWhile([]int{0, 1, 2, 3, 4, 5, 6}, func(t int) bool { - return t != 10 - })) -} - -func TestReject(t *testing.T) { - t.Parallel() - is := assert.New(t) - - r1 := Reject([]int{1, 2, 3, 4}, func(x int, _ int) bool { - return x%2 == 0 - }) - - is.Equal(r1, []int{1, 3}) - - r2 := Reject([]string{"Smith", "foo", "Domin", "bar", "Olivia"}, func(x string, _ int) bool { - return len(x) > 3 - }) - - is.Equal(r2, []string{"foo", "bar"}) -} - -func TestCount(t *testing.T) { - t.Parallel() - is := assert.New(t) - - count1 := Count([]int{1, 2, 1}, 1) - count2 := Count([]int{1, 2, 1}, 3) - count3 := Count([]int{}, 1) - - is.Equal(count1, 2) - is.Equal(count2, 0) - is.Equal(count3, 0) -} - -func TestCountBy(t *testing.T) { - t.Parallel() - is := assert.New(t) - - count1 := CountBy([]int{1, 2, 1}, func(i int) bool { - return i < 2 - }) - - count2 := CountBy([]int{1, 2, 1}, func(i int) bool { - return i > 2 - }) - - count3 := CountBy([]int{}, func(i int) bool { - return i <= 2 - }) - - is.Equal(count1, 2) - is.Equal(count2, 0) - is.Equal(count3, 0) -} - -func TestCountValues(t *testing.T) { - t.Parallel() - is := assert.New(t) - - is.Equal(map[int]int{}, CountValues([]int{})) - is.Equal(map[int]int{1: 1, 2: 1}, CountValues([]int{1, 2})) - is.Equal(map[int]int{1: 1, 2: 2}, CountValues([]int{1, 2, 2})) - is.Equal(map[string]int{"": 1, "foo": 1, "bar": 1}, CountValues([]string{"foo", "bar", ""})) - is.Equal(map[string]int{"foo": 1, "bar": 2}, CountValues([]string{"foo", "bar", "bar"})) -} - -func TestCountValuesBy(t *testing.T) { - t.Parallel() - is := assert.New(t) - - oddEven := func(v int) bool { - return v%2 == 0 - } - length := func(v string) int { - return len(v) - } - - result1 := CountValuesBy([]int{}, oddEven) - result2 := CountValuesBy([]int{1, 2}, oddEven) - result3 := CountValuesBy([]int{1, 2, 2}, oddEven) - result4 := CountValuesBy([]string{"foo", "bar", ""}, length) - result5 := CountValuesBy([]string{"foo", "bar", "bar"}, length) - - is.Equal(map[bool]int{}, result1) - is.Equal(map[bool]int{true: 1, false: 1}, result2) - is.Equal(map[bool]int{true: 2, false: 1}, result3) - is.Equal(map[int]int{0: 1, 3: 2}, result4) - is.Equal(map[int]int{3: 3}, result5) -} - -func TestSubset(t *testing.T) { - t.Parallel() - is := assert.New(t) - - in := []int{0, 1, 2, 3, 4} - - out1 := Subset(in, 0, 0) - out2 := Subset(in, 10, 2) - out3 := Subset(in, -10, 2) - out4 := Subset(in, 0, 10) - out5 := Subset(in, 0, 2) - out6 := Subset(in, 2, 2) - out7 := Subset(in, 2, 5) - out8 := Subset(in, 2, 3) - out9 := Subset(in, 2, 4) - out10 := Subset(in, -2, 4) - out11 := Subset(in, -4, 1) - out12 := Subset(in, -4, math.MaxUint) - - is.Equal([]int{}, out1) - is.Equal([]int{}, out2) - is.Equal([]int{0, 1}, out3) - is.Equal([]int{0, 1, 2, 3, 4}, out4) - is.Equal([]int{0, 1}, out5) - is.Equal([]int{2, 3}, out6) - is.Equal([]int{2, 3, 4}, out7) - is.Equal([]int{2, 3, 4}, out8) - is.Equal([]int{2, 3, 4}, out9) - is.Equal([]int{3, 4}, out10) - is.Equal([]int{1}, out11) - is.Equal([]int{1, 2, 3, 4}, out12) -} - -func TestSlice(t *testing.T) { - t.Parallel() - is := assert.New(t) - - in := []int{0, 1, 2, 3, 4} - - out1 := Slice(in, 0, 0) - out2 := Slice(in, 0, 1) - out3 := Slice(in, 0, 5) - out4 := Slice(in, 0, 6) - out5 := Slice(in, 1, 1) - out6 := Slice(in, 1, 5) - out7 := Slice(in, 1, 6) - out8 := Slice(in, 4, 5) - out9 := Slice(in, 5, 5) - out10 := Slice(in, 6, 5) - out11 := Slice(in, 6, 6) - out12 := Slice(in, 1, 0) - out13 := Slice(in, 5, 0) - out14 := Slice(in, 6, 4) - out15 := Slice(in, 6, 7) - out16 := Slice(in, -10, 1) - out17 := Slice(in, -1, 3) - out18 := Slice(in, -10, 7) - - is.Equal([]int{}, out1) - is.Equal([]int{0}, out2) - is.Equal([]int{0, 1, 2, 3, 4}, out3) - is.Equal([]int{0, 1, 2, 3, 4}, out4) - is.Equal([]int{}, out5) - is.Equal([]int{1, 2, 3, 4}, out6) - is.Equal([]int{1, 2, 3, 4}, out7) - is.Equal([]int{4}, out8) - is.Equal([]int{}, out9) - is.Equal([]int{}, out10) - is.Equal([]int{}, out11) - is.Equal([]int{}, out12) - is.Equal([]int{}, out13) - is.Equal([]int{}, out14) - is.Equal([]int{}, out15) - is.Equal([]int{0}, out16) - is.Equal([]int{0, 1, 2}, out17) - is.Equal([]int{0, 1, 2, 3, 4}, out18) -} - -func TestReplace(t *testing.T) { - t.Parallel() - is := assert.New(t) - - in := []int{0, 1, 0, 1, 2, 3, 0} - - out1 := Replace(in, 0, 42, 2) - out2 := Replace(in, 0, 42, 1) - out3 := Replace(in, 0, 42, 0) - out4 := Replace(in, 0, 42, -1) - out5 := Replace(in, 0, 42, -1) - out6 := Replace(in, -1, 42, 2) - out7 := Replace(in, -1, 42, 1) - out8 := Replace(in, -1, 42, 0) - out9 := Replace(in, -1, 42, -1) - out10 := Replace(in, -1, 42, -1) - - is.Equal([]int{42, 1, 42, 1, 2, 3, 0}, out1) - is.Equal([]int{42, 1, 0, 1, 2, 3, 0}, out2) - is.Equal([]int{0, 1, 0, 1, 2, 3, 0}, out3) - is.Equal([]int{42, 1, 42, 1, 2, 3, 42}, out4) - is.Equal([]int{42, 1, 42, 1, 2, 3, 42}, out5) - is.Equal([]int{0, 1, 0, 1, 2, 3, 0}, out6) - is.Equal([]int{0, 1, 0, 1, 2, 3, 0}, out7) - is.Equal([]int{0, 1, 0, 1, 2, 3, 0}, out8) - is.Equal([]int{0, 1, 0, 1, 2, 3, 0}, out9) - is.Equal([]int{0, 1, 0, 1, 2, 3, 0}, out10) -} - -func TestReplaceAll(t *testing.T) { - t.Parallel() - is := assert.New(t) - - in := []int{0, 1, 0, 1, 2, 3, 0} - - out1 := ReplaceAll(in, 0, 42) - out2 := ReplaceAll(in, -1, 42) - - is.Equal([]int{42, 1, 42, 1, 2, 3, 42}, out1) - is.Equal([]int{0, 1, 0, 1, 2, 3, 0}, out2) -} - -func TestCompact(t *testing.T) { - t.Parallel() - is := assert.New(t) - - r1 := Compact([]int{2, 0, 4, 0}) - - is.Equal(r1, []int{2, 4}) - - r2 := Compact([]string{"", "foo", "", "bar", ""}) - - is.Equal(r2, []string{"foo", "bar"}) - - r3 := Compact([]bool{true, false, true, false}) - - is.Equal(r3, []bool{true, true}) - - type foo struct { - bar int - baz string - } - - // slice of structs - // If all fields of an element are zero values, Compact removes it. - - r4 := Compact([]foo{ - {bar: 1, baz: "a"}, // all fields are non-zero values - {bar: 0, baz: ""}, // all fields are zero values - {bar: 2, baz: ""}, // bar is non-zero - }) - - is.Equal(r4, []foo{{bar: 1, baz: "a"}, {bar: 2, baz: ""}}) - - // slice of pointers to structs - // If an element is nil, Compact removes it. - - e1, e2, e3 := foo{bar: 1, baz: "a"}, foo{bar: 0, baz: ""}, foo{bar: 2, baz: ""} - // NOTE: e2 is a zero value of foo, but its pointer &e2 is not a zero value of *foo. - r5 := Compact([]*foo{&e1, &e2, nil, &e3}) - - is.Equal(r5, []*foo{&e1, &e2, &e3}) -} - -func TestIsSorted(t *testing.T) { - t.Parallel() - is := assert.New(t) - - is.True(IsSorted([]int{0, 1, 2, 3, 4, 5, 6, 7, 8, 9})) - is.True(IsSorted([]string{"a", "b", "c", "d", "e", "f", "g", "h", "i", "j"})) - - is.False(IsSorted([]int{0, 1, 4, 3, 2, 5, 6, 7, 8, 9, 10})) - is.False(IsSorted([]string{"a", "b", "d", "c", "e", "f", "g", "h", "i", "j"})) -} - -func TestIsSortedByKey(t *testing.T) { - t.Parallel() - is := assert.New(t) - - is.True(IsSortedByKey([]string{"a", "bb", "ccc"}, func(s string) int { - return len(s) - })) - - is.False(IsSortedByKey([]string{"aa", "b", "ccc"}, func(s string) int { - return len(s) - })) - - is.True(IsSortedByKey([]string{"1", "2", "3", "11"}, func(s string) int { - ret, _ := strconv.Atoi(s) - return ret - })) -} diff --git a/string_example_test.go b/string_example_test.go deleted file mode 100644 index b659ea14..00000000 --- a/string_example_test.go +++ /dev/null @@ -1,54 +0,0 @@ -package lo - -import ( - "fmt" - "math" -) - -func ExampleSubstring() { - result1 := Substring("hello", 2, 3) - result2 := Substring("hello", -4, 3) - result3 := Substring("hello", -2, math.MaxUint) - result4 := Substring("🏠🐶🐱", 0, 2) - result5 := Substring("你好,世界", 0, 3) - - fmt.Printf("%v\n", result1) - fmt.Printf("%v\n", result2) - fmt.Printf("%v\n", result3) - fmt.Printf("%v\n", result4) - fmt.Printf("%v\n", result5) - // Output: - // llo - // ell - // lo - // 🏠🐶 - // 你好, -} - -func ExampleChunkString() { - result1 := ChunkString("123456", 2) - result2 := ChunkString("1234567", 2) - result3 := ChunkString("", 2) - result4 := ChunkString("1", 2) - - fmt.Printf("%v\n", result1) - fmt.Printf("%v\n", result2) - fmt.Printf("%v\n", result3) - fmt.Printf("%v\n", result4) - // Output: - // [12 34 56] - // [12 34 56 7] - // [] - // [1] -} - -func ExampleRuneLength() { - result1, chars1 := RuneLength("hellô"), len("hellô") - result2, chars2 := RuneLength("🤘"), len("🤘") - - fmt.Printf("%v %v\n", result1, chars1) - fmt.Printf("%v %v\n", result2, chars2) - // Output: - // 5 6 - // 1 4 -} diff --git a/string_test.go b/string_test.go deleted file mode 100644 index 42832586..00000000 --- a/string_test.go +++ /dev/null @@ -1,102 +0,0 @@ -package lo - -import ( - "math" - "math/rand" - "testing" - "time" - - "github.com/stretchr/testify/assert" -) - -func TestRandomString(t *testing.T) { - t.Parallel() - is := assert.New(t) - - rand.Seed(time.Now().UnixNano()) - - str1 := RandomString(100, LowerCaseLettersCharset) - is.Equal(100, RuneLength(str1)) - is.Subset(LowerCaseLettersCharset, []rune(str1)) - - str2 := RandomString(100, LowerCaseLettersCharset) - is.NotEqual(str1, str2) - - noneUtf8Charset := []rune("明1好休2林森") - str3 := RandomString(100, noneUtf8Charset) - is.Equal(100, RuneLength(str3)) - is.Subset(noneUtf8Charset, []rune(str3)) - - is.PanicsWithValue("lo.RandomString: Charset parameter must not be empty", func() { RandomString(100, []rune{}) }) - is.PanicsWithValue("lo.RandomString: Size parameter must be greater than 0", func() { RandomString(0, LowerCaseLettersCharset) }) -} - -func TestChunkString(t *testing.T) { - t.Parallel() - is := assert.New(t) - - result1 := ChunkString("12345", 2) - is.Equal([]string{"12", "34", "5"}, result1) - - result2 := ChunkString("123456", 2) - is.Equal([]string{"12", "34", "56"}, result2) - - result3 := ChunkString("123456", 6) - is.Equal([]string{"123456"}, result3) - - result4 := ChunkString("123456", 10) - is.Equal([]string{"123456"}, result4) - - result5 := ChunkString("", 2) - is.Equal([]string{""}, result5) - - result6 := ChunkString("明1好休2林森", 2) - is.Equal([]string{"明1", "好休", "2林", "森"}, result6) - - is.Panics(func() { - ChunkString("12345", 0) - }) -} - -func TestSubstring(t *testing.T) { - t.Parallel() - is := assert.New(t) - - str1 := Substring("hello", 0, 0) - str2 := Substring("hello", 10, 2) - str3 := Substring("hello", -10, 2) - str4 := Substring("hello", 0, 10) - str5 := Substring("hello", 0, 2) - str6 := Substring("hello", 2, 2) - str7 := Substring("hello", 2, 5) - str8 := Substring("hello", 2, 3) - str9 := Substring("hello", 2, 4) - str10 := Substring("hello", -2, 4) - str11 := Substring("hello", -4, 1) - str12 := Substring("hello", -4, math.MaxUint) - str13 := Substring("🏠🐶🐱", 0, 2) - str14 := Substring("你好,世界", 0, 3) - - is.Equal("", str1) - is.Equal("", str2) - is.Equal("he", str3) - is.Equal("hello", str4) - is.Equal("he", str5) - is.Equal("ll", str6) - is.Equal("llo", str7) - is.Equal("llo", str8) - is.Equal("llo", str9) - is.Equal("lo", str10) - is.Equal("e", str11) - is.Equal("ello", str12) - is.Equal("🏠🐶", str13) - is.Equal("你好,", str14) -} - -func TestRuneLength(t *testing.T) { - t.Parallel() - is := assert.New(t) - - is.Equal(5, RuneLength("hellô")) - is.Equal(6, len("hellô")) -} diff --git a/tuples_example_test.go b/tuples_example_test.go deleted file mode 100644 index b8eb2e99..00000000 --- a/tuples_example_test.go +++ /dev/null @@ -1,197 +0,0 @@ -package lo - -import ( - "fmt" -) - -func ExampleT2() { - result := T2("hello", 2) - fmt.Printf("%v %v", result.A, result.B) - // Output: hello 2 -} - -func ExampleT3() { - result := T3("hello", 2, true) - fmt.Printf("%v %v %v", result.A, result.B, result.C) - // Output: hello 2 true -} - -func ExampleT4() { - result := T4("hello", 2, true, foo{bar: "bar"}) - fmt.Printf("%v %v %v %v", result.A, result.B, result.C, result.D) - // Output: hello 2 true {bar} -} - -func ExampleT5() { - result := T5("hello", 2, true, foo{bar: "bar"}, 4.2) - fmt.Printf("%v %v %v %v %v", result.A, result.B, result.C, result.D, result.E) - // Output: hello 2 true {bar} 4.2 -} - -func ExampleT6() { - result := T6("hello", 2, true, foo{bar: "bar"}, 4.2, "plop") - fmt.Printf("%v %v %v %v %v %v", result.A, result.B, result.C, result.D, result.E, result.F) - // Output: hello 2 true {bar} 4.2 plop -} - -func ExampleT7() { - result := T7("hello", 2, true, foo{bar: "bar"}, 4.2, "plop", false) - fmt.Printf("%v %v %v %v %v %v %v", result.A, result.B, result.C, result.D, result.E, result.F, result.G) - // Output: hello 2 true {bar} 4.2 plop false -} - -func ExampleT8() { - result := T8("hello", 2, true, foo{bar: "bar"}, 4.2, "plop", false, 42) - fmt.Printf("%v %v %v %v %v %v %v %v", result.A, result.B, result.C, result.D, result.E, result.F, result.G, result.H) - // Output: hello 2 true {bar} 4.2 plop false 42 -} - -func ExampleT9() { - result := T9("hello", 2, true, foo{bar: "bar"}, 4.2, "plop", false, 42, "hello world") - fmt.Printf("%v %v %v %v %v %v %v %v %v", result.A, result.B, result.C, result.D, result.E, result.F, result.G, result.H, result.I) - // Output: hello 2 true {bar} 4.2 plop false 42 hello world -} - -func ExampleUnpack2() { - a, b := Unpack2(T2("hello", 2)) - fmt.Printf("%v %v", a, b) - // Output: hello 2 -} - -func ExampleUnpack3() { - a, b, c := Unpack3(T3("hello", 2, true)) - fmt.Printf("%v %v %v", a, b, c) - // Output: hello 2 true -} - -func ExampleUnpack4() { - a, b, c, d := Unpack4(T4("hello", 2, true, foo{bar: "bar"})) - fmt.Printf("%v %v %v %v", a, b, c, d) - // Output: hello 2 true {bar} -} - -func ExampleUnpack5() { - a, b, c, d, e := Unpack5(T5("hello", 2, true, foo{bar: "bar"}, 4.2)) - fmt.Printf("%v %v %v %v %v", a, b, c, d, e) - // Output: hello 2 true {bar} 4.2 -} - -func ExampleUnpack6() { - a, b, c, d, e, f := Unpack6(T6("hello", 2, true, foo{bar: "bar"}, 4.2, "plop")) - fmt.Printf("%v %v %v %v %v %v", a, b, c, d, e, f) - // Output: hello 2 true {bar} 4.2 plop -} - -func ExampleUnpack7() { - a, b, c, d, e, f, g := Unpack7(T7("hello", 2, true, foo{bar: "bar"}, 4.2, "plop", false)) - fmt.Printf("%v %v %v %v %v %v %v", a, b, c, d, e, f, g) - // Output: hello 2 true {bar} 4.2 plop false -} - -func ExampleUnpack8() { - a, b, c, d, e, f, g, h := Unpack8(T8("hello", 2, true, foo{bar: "bar"}, 4.2, "plop", false, 42)) - fmt.Printf("%v %v %v %v %v %v %v %v", a, b, c, d, e, f, g, h) - // Output: hello 2 true {bar} 4.2 plop false 42 -} - -func ExampleUnpack9() { - a, b, c, d, e, f, g, h, i := Unpack9(T9("hello", 2, true, foo{bar: "bar"}, 4.2, "plop", false, 42, "hello world")) - fmt.Printf("%v %v %v %v %v %v %v %v %v", a, b, c, d, e, f, g, h, i) - // Output: hello 2 true {bar} 4.2 plop false 42 hello world -} - -func ExampleZip2() { - result := Zip2([]string{"hello"}, []int{2}) - fmt.Printf("%v", result) - // Output: [{hello 2}] -} - -func ExampleZip3() { - result := Zip3([]string{"hello"}, []int{2}, []bool{true}) - fmt.Printf("%v", result) - // Output: [{hello 2 true}] -} - -func ExampleZip4() { - result := Zip4([]string{"hello"}, []int{2}, []bool{true}, []foo{{bar: "bar"}}) - fmt.Printf("%v", result) - // Output: [{hello 2 true {bar}}] -} - -func ExampleZip5() { - result := Zip5([]string{"hello"}, []int{2}, []bool{true}, []foo{{bar: "bar"}}, []float64{4.2}) - fmt.Printf("%v", result) - // Output: [{hello 2 true {bar} 4.2}] -} - -func ExampleZip6() { - result := Zip6([]string{"hello"}, []int{2}, []bool{true}, []foo{{bar: "bar"}}, []float64{4.2}, []string{"plop"}) - fmt.Printf("%v", result) - // Output: [{hello 2 true {bar} 4.2 plop}] -} - -func ExampleZip7() { - result := Zip7([]string{"hello"}, []int{2}, []bool{true}, []foo{{bar: "bar"}}, []float64{4.2}, []string{"plop"}, []bool{false}) - fmt.Printf("%v", result) - // Output: [{hello 2 true {bar} 4.2 plop false}] -} - -func ExampleZip8() { - result := Zip8([]string{"hello"}, []int{2}, []bool{true}, []foo{{bar: "bar"}}, []float64{4.2}, []string{"plop"}, []bool{false}, []int{42}) - fmt.Printf("%v", result) - // Output: [{hello 2 true {bar} 4.2 plop false 42}] -} - -func ExampleZip9() { - result := Zip9([]string{"hello"}, []int{2}, []bool{true}, []foo{{bar: "bar"}}, []float64{4.2}, []string{"plop"}, []bool{false}, []int{42}, []string{"hello world"}) - fmt.Printf("%v", result) - // Output: [{hello 2 true {bar} 4.2 plop false 42 hello world}] -} - -func ExampleUnzip2() { - a, b := Unzip2([]Tuple2[string, int]{T2("hello", 2)}) - fmt.Printf("%v %v", a, b) - // Output: [hello] [2] -} - -func ExampleUnzip3() { - a, b, c := Unzip3([]Tuple3[string, int, bool]{T3("hello", 2, true)}) - fmt.Printf("%v %v %v", a, b, c) - // Output: [hello] [2] [true] -} - -func ExampleUnzip4() { - a, b, c, d := Unzip4([]Tuple4[string, int, bool, foo]{T4("hello", 2, true, foo{bar: "bar"})}) - fmt.Printf("%v %v %v %v", a, b, c, d) - // Output: [hello] [2] [true] [{bar}] -} - -func ExampleUnzip5() { - a, b, c, d, e := Unzip5([]Tuple5[string, int, bool, foo, float64]{T5("hello", 2, true, foo{bar: "bar"}, 4.2)}) - fmt.Printf("%v %v %v %v %v", a, b, c, d, e) - // Output: [hello] [2] [true] [{bar}] [4.2] -} - -func ExampleUnzip6() { - a, b, c, d, e, f := Unzip6([]Tuple6[string, int, bool, foo, float64, string]{T6("hello", 2, true, foo{bar: "bar"}, 4.2, "plop")}) - fmt.Printf("%v %v %v %v %v %v", a, b, c, d, e, f) - // Output: [hello] [2] [true] [{bar}] [4.2] [plop] -} - -func ExampleUnzip7() { - a, b, c, d, e, f, g := Unzip7([]Tuple7[string, int, bool, foo, float64, string, bool]{T7("hello", 2, true, foo{bar: "bar"}, 4.2, "plop", false)}) - fmt.Printf("%v %v %v %v %v %v %v", a, b, c, d, e, f, g) - // Output: [hello] [2] [true] [{bar}] [4.2] [plop] [false] -} - -func ExampleUnzip8() { - a, b, c, d, e, f, g, h := Unzip8([]Tuple8[string, int, bool, foo, float64, string, bool, int]{T8("hello", 2, true, foo{bar: "bar"}, 4.2, "plop", false, 42)}) - fmt.Printf("%v %v %v %v %v %v %v %v", a, b, c, d, e, f, g, h) - // Output: [hello] [2] [true] [{bar}] [4.2] [plop] [false] [42] -} - -func ExampleUnzip9() { - a, b, c, d, e, f, g, h, i := Unzip9([]Tuple9[string, int, bool, foo, float64, string, bool, int, string]{T9("hello", 2, true, foo{bar: "bar"}, 4.2, "plop", false, 42, "hello world")}) - fmt.Printf("%v %v %v %v %v %v %v %v %v", a, b, c, d, e, f, g, h, i) - // Output: [hello] [2] [true] [{bar}] [4.2] [plop] [false] [42] [hello world] -} diff --git a/tuples_test.go b/tuples_test.go deleted file mode 100644 index b5aac617..00000000 --- a/tuples_test.go +++ /dev/null @@ -1,353 +0,0 @@ -package lo - -import ( - "testing" - - "github.com/stretchr/testify/assert" -) - -func TestT(t *testing.T) { - t.Parallel() - is := assert.New(t) - - r1 := T2("a", 1) - r2 := T3[string, int, float32]("b", 2, 3.0) - r3 := T4[string, int, float32]("c", 3, 4.0, true) - r4 := T5[string, int, float32]("d", 4, 5.0, false, "e") - r5 := T6[string, int, float32]("f", 5, 6.0, true, "g", 7) - r6 := T7[string, int, float32]("h", 6, 7.0, false, "i", 8, 9.0) - r7 := T8[string, int, float32]("j", 7, 8.0, true, "k", 9, 10.0, false) - r8 := T9[string, int, float32]("l", 8, 9.0, false, "m", 10, 11.0, true, "n") - - is.Equal(r1, Tuple2[string, int]{A: "a", B: 1}) - is.Equal(r2, Tuple3[string, int, float32]{A: "b", B: 2, C: 3.0}) - is.Equal(r3, Tuple4[string, int, float32, bool]{A: "c", B: 3, C: 4.0, D: true}) - is.Equal(r4, Tuple5[string, int, float32, bool, string]{A: "d", B: 4, C: 5.0, D: false, E: "e"}) - is.Equal(r5, Tuple6[string, int, float32, bool, string, int]{A: "f", B: 5, C: 6.0, D: true, E: "g", F: 7}) - is.Equal(r6, Tuple7[string, int, float32, bool, string, int, float64]{A: "h", B: 6, C: 7.0, D: false, E: "i", F: 8, G: 9.0}) - is.Equal(r7, Tuple8[string, int, float32, bool, string, int, float64, bool]{A: "j", B: 7, C: 8.0, D: true, E: "k", F: 9, G: 10.0, H: false}) - is.Equal(r8, Tuple9[string, int, float32, bool, string, int, float64, bool, string]{A: "l", B: 8, C: 9.0, D: false, E: "m", F: 10, G: 11.0, H: true, I: "n"}) -} - -func TestUnpack(t *testing.T) { - t.Parallel() - is := assert.New(t) - - { - tuple := Tuple2[string, int]{"a", 1} - - r1, r2 := Unpack2(tuple) - - is.Equal("a", r1) - is.Equal(1, r2) - - r1, r2 = tuple.Unpack() - - is.Equal("a", r1) - is.Equal(1, r2) - } - - { - tuple := Tuple3[string, int, float64]{"a", 1, 1.0} - - r1, r2, r3 := Unpack3(tuple) - - is.Equal("a", r1) - is.Equal(1, r2) - is.Equal(1.0, r3) - - r1, r2, r3 = tuple.Unpack() - - is.Equal("a", r1) - is.Equal(1, r2) - is.Equal(1.0, r3) - } - - { - tuple := Tuple4[string, int, float64, bool]{"a", 1, 1.0, true} - - r1, r2, r3, r4 := Unpack4(tuple) - - is.Equal("a", r1) - is.Equal(1, r2) - is.Equal(1.0, r3) - is.Equal(true, r4) - - r1, r2, r3, r4 = tuple.Unpack() - - is.Equal("a", r1) - is.Equal(1, r2) - is.Equal(1.0, r3) - is.Equal(true, r4) - } - - { - tuple := Tuple5[string, int, float64, bool, string]{"a", 1, 1.0, true, "b"} - - r1, r2, r3, r4, r5 := Unpack5(tuple) - - is.Equal("a", r1) - is.Equal(1, r2) - is.Equal(1.0, r3) - is.Equal(true, r4) - is.Equal("b", r5) - - r1, r2, r3, r4, r5 = tuple.Unpack() - - is.Equal("a", r1) - is.Equal(1, r2) - is.Equal(1.0, r3) - is.Equal(true, r4) - is.Equal("b", r5) - } - - { - tuple := Tuple6[string, int, float64, bool, string, int]{"a", 1, 1.0, true, "b", 2} - - r1, r2, r3, r4, r5, r6 := Unpack6(tuple) - - is.Equal("a", r1) - is.Equal(1, r2) - is.Equal(1.0, r3) - is.Equal(true, r4) - is.Equal("b", r5) - is.Equal(2, r6) - - r1, r2, r3, r4, r5, r6 = tuple.Unpack() - - is.Equal("a", r1) - is.Equal(1, r2) - is.Equal(1.0, r3) - is.Equal(true, r4) - is.Equal("b", r5) - is.Equal(2, r6) - } - - { - tuple := Tuple7[string, int, float64, bool, string, int, float64]{"a", 1, 1.0, true, "b", 2, 3.0} - - r1, r2, r3, r4, r5, r6, r7 := Unpack7(tuple) - - is.Equal("a", r1) - is.Equal(1, r2) - is.Equal(1.0, r3) - is.Equal(true, r4) - is.Equal("b", r5) - is.Equal(2, r6) - is.Equal(3.0, r7) - - r1, r2, r3, r4, r5, r6, r7 = tuple.Unpack() - - is.Equal("a", r1) - is.Equal(1, r2) - is.Equal(1.0, r3) - is.Equal(true, r4) - is.Equal("b", r5) - is.Equal(2, r6) - is.Equal(3.0, r7) - } - - { - tuple := Tuple8[string, int, float64, bool, string, int, float64, bool]{"a", 1, 1.0, true, "b", 2, 3.0, true} - - r1, r2, r3, r4, r5, r6, r7, r8 := Unpack8(tuple) - - is.Equal("a", r1) - is.Equal(1, r2) - is.Equal(1.0, r3) - is.Equal(true, r4) - is.Equal("b", r5) - is.Equal(2, r6) - is.Equal(3.0, r7) - is.Equal(true, r8) - - r1, r2, r3, r4, r5, r6, r7, r8 = tuple.Unpack() - - is.Equal("a", r1) - is.Equal(1, r2) - is.Equal(1.0, r3) - is.Equal(true, r4) - is.Equal("b", r5) - is.Equal(2, r6) - is.Equal(3.0, r7) - is.Equal(true, r8) - } - - { - tuple := Tuple9[string, int, float64, bool, string, int, float64, bool, string]{"a", 1, 1.0, true, "b", 2, 3.0, true, "c"} - - r1, r2, r3, r4, r5, r6, r7, r8, r9 := Unpack9(tuple) - - is.Equal("a", r1) - is.Equal(1, r2) - is.Equal(1.0, r3) - is.Equal(true, r4) - is.Equal("b", r5) - is.Equal(2, r6) - is.Equal(3.0, r7) - is.Equal(true, r8) - is.Equal("c", r9) - - r1, r2, r3, r4, r5, r6, r7, r8, r9 = tuple.Unpack() - - is.Equal("a", r1) - is.Equal(1, r2) - is.Equal(1.0, r3) - is.Equal(true, r4) - is.Equal("b", r5) - is.Equal(2, r6) - is.Equal(3.0, r7) - is.Equal(true, r8) - is.Equal("c", r9) - } -} - -func TestZip(t *testing.T) { - t.Parallel() - is := assert.New(t) - - r1 := Zip2( - []string{"a", "b"}, - []int{1, 2}, - ) - - r2 := Zip3( - []string{"a", "b", "c"}, - []int{1, 2, 3}, []int{4, 5, 6}, - ) - - r3 := Zip4( - []string{"a", "b", "c", "d"}, - []int{1, 2, 3, 4}, - []int{5, 6, 7, 8}, - []bool{true, true, true, true}, - ) - - r4 := Zip5( - []string{"a", "b", "c", "d", "e"}, - []int{1, 2, 3, 4, 5}, - []int{6, 7, 8, 9, 10}, - []bool{true, true, true, true, true}, - []float32{0.1, 0.2, 0.3, 0.4, 0.5}, - ) - - r5 := Zip6( - []string{"a", "b", "c", "d", "e", "f"}, - []int{1, 2, 3, 4, 5, 6}, - []int{7, 8, 9, 10, 11, 12}, - []bool{true, true, true, true, true, true}, - []float32{0.1, 0.2, 0.3, 0.4, 0.5, 0.6}, - []float64{0.01, 0.02, 0.03, 0.04, 0.05, 0.06}, - ) - - r6 := Zip7( - []string{"a", "b", "c", "d", "e", "f", "g"}, - []int{1, 2, 3, 4, 5, 6, 7}, - []int{8, 9, 10, 11, 12, 13, 14}, - []bool{true, true, true, true, true, true, true}, - []float32{0.1, 0.2, 0.3, 0.4, 0.5, 0.6, 0.7}, - []float64{0.01, 0.02, 0.03, 0.04, 0.05, 0.06, 0.07}, - []int8{1, 2, 3, 4, 5, 6, 7}, - ) - - r7 := Zip8( - []string{"a", "b", "c", "d", "e", "f", "g", "h"}, - []int{1, 2, 3, 4, 5, 6, 7, 8}, - []int{9, 10, 11, 12, 13, 14, 15, 16}, - []bool{true, true, true, true, true, true, true, true}, - []float32{0.1, 0.2, 0.3, 0.4, 0.5, 0.6, 0.7, 0.8}, - []float64{0.01, 0.02, 0.03, 0.04, 0.05, 0.06, 0.07, 0.08}, - []int8{1, 2, 3, 4, 5, 6, 7, 8}, - []int16{1, 2, 3, 4, 5, 6, 7, 8}, - ) - - r8 := Zip9( - []string{"a", "b", "c", "d", "e", "f", "g", "h", "i"}, - []int{1, 2, 3, 4, 5, 6, 7, 8, 9}, - []int{10, 11, 12, 13, 14, 15, 16, 17, 18}, - []bool{true, true, true, true, true, true, true, true, true}, - []float32{0.1, 0.2, 0.3, 0.4, 0.5, 0.6, 0.7, 0.8, 0.9}, - []float64{0.01, 0.02, 0.03, 0.04, 0.05, 0.06, 0.07, 0.08, 0.09}, - []int8{1, 2, 3, 4, 5, 6, 7, 8, 9}, - []int16{1, 2, 3, 4, 5, 6, 7, 8, 9}, - []int32{1, 2, 3, 4, 5, 6, 7, 8, 9}, - ) - - is.Equal(r1, []Tuple2[string, int]{ - {A: "a", B: 1}, - {A: "b", B: 2}, - }) - - is.Equal(r2, []Tuple3[string, int, int]{ - {A: "a", B: 1, C: 4}, - {A: "b", B: 2, C: 5}, - {A: "c", B: 3, C: 6}, - }) - - is.Equal(r3, []Tuple4[string, int, int, bool]{ - {A: "a", B: 1, C: 5, D: true}, - {A: "b", B: 2, C: 6, D: true}, - {A: "c", B: 3, C: 7, D: true}, - {A: "d", B: 4, C: 8, D: true}, - }) - - is.Equal(r4, []Tuple5[string, int, int, bool, float32]{ - {A: "a", B: 1, C: 6, D: true, E: 0.1}, - {A: "b", B: 2, C: 7, D: true, E: 0.2}, - {A: "c", B: 3, C: 8, D: true, E: 0.3}, - {A: "d", B: 4, C: 9, D: true, E: 0.4}, - {A: "e", B: 5, C: 10, D: true, E: 0.5}, - }) - - is.Equal(r5, []Tuple6[string, int, int, bool, float32, float64]{ - {A: "a", B: 1, C: 7, D: true, E: 0.1, F: 0.01}, - {A: "b", B: 2, C: 8, D: true, E: 0.2, F: 0.02}, - {A: "c", B: 3, C: 9, D: true, E: 0.3, F: 0.03}, - {A: "d", B: 4, C: 10, D: true, E: 0.4, F: 0.04}, - {A: "e", B: 5, C: 11, D: true, E: 0.5, F: 0.05}, - {A: "f", B: 6, C: 12, D: true, E: 0.6, F: 0.06}, - }) - - is.Equal(r6, []Tuple7[string, int, int, bool, float32, float64, int8]{ - {A: "a", B: 1, C: 8, D: true, E: 0.1, F: 0.01, G: 1}, - {A: "b", B: 2, C: 9, D: true, E: 0.2, F: 0.02, G: 2}, - {A: "c", B: 3, C: 10, D: true, E: 0.3, F: 0.03, G: 3}, - {A: "d", B: 4, C: 11, D: true, E: 0.4, F: 0.04, G: 4}, - {A: "e", B: 5, C: 12, D: true, E: 0.5, F: 0.05, G: 5}, - {A: "f", B: 6, C: 13, D: true, E: 0.6, F: 0.06, G: 6}, - {A: "g", B: 7, C: 14, D: true, E: 0.7, F: 0.07, G: 7}, - }) - - is.Equal(r7, []Tuple8[string, int, int, bool, float32, float64, int8, int16]{ - {A: "a", B: 1, C: 9, D: true, E: 0.1, F: 0.01, G: 1, H: 1}, - {A: "b", B: 2, C: 10, D: true, E: 0.2, F: 0.02, G: 2, H: 2}, - {A: "c", B: 3, C: 11, D: true, E: 0.3, F: 0.03, G: 3, H: 3}, - {A: "d", B: 4, C: 12, D: true, E: 0.4, F: 0.04, G: 4, H: 4}, - {A: "e", B: 5, C: 13, D: true, E: 0.5, F: 0.05, G: 5, H: 5}, - {A: "f", B: 6, C: 14, D: true, E: 0.6, F: 0.06, G: 6, H: 6}, - {A: "g", B: 7, C: 15, D: true, E: 0.7, F: 0.07, G: 7, H: 7}, - {A: "h", B: 8, C: 16, D: true, E: 0.8, F: 0.08, G: 8, H: 8}, - }) - - is.Equal(r8, []Tuple9[string, int, int, bool, float32, float64, int8, int16, int32]{ - {A: "a", B: 1, C: 10, D: true, E: 0.1, F: 0.01, G: 1, H: 1, I: 1}, - {A: "b", B: 2, C: 11, D: true, E: 0.2, F: 0.02, G: 2, H: 2, I: 2}, - {A: "c", B: 3, C: 12, D: true, E: 0.3, F: 0.03, G: 3, H: 3, I: 3}, - {A: "d", B: 4, C: 13, D: true, E: 0.4, F: 0.04, G: 4, H: 4, I: 4}, - {A: "e", B: 5, C: 14, D: true, E: 0.5, F: 0.05, G: 5, H: 5, I: 5}, - {A: "f", B: 6, C: 15, D: true, E: 0.6, F: 0.06, G: 6, H: 6, I: 6}, - {A: "g", B: 7, C: 16, D: true, E: 0.7, F: 0.07, G: 7, H: 7, I: 7}, - {A: "h", B: 8, C: 17, D: true, E: 0.8, F: 0.08, G: 8, H: 8, I: 8}, - {A: "i", B: 9, C: 18, D: true, E: 0.9, F: 0.09, G: 9, H: 9, I: 9}, - }) -} - -func TestUnzip(t *testing.T) { - t.Parallel() - is := assert.New(t) - - r1, r2 := Unzip2([]Tuple2[string, int]{{A: "a", B: 1}, {A: "b", B: 2}}) - - is.Equal(r1, []string{"a", "b"}) - is.Equal(r2, []int{1, 2}) -} diff --git a/type_manipulation_test.go b/type_manipulation_test.go deleted file mode 100644 index 48e3676f..00000000 --- a/type_manipulation_test.go +++ /dev/null @@ -1,211 +0,0 @@ -package lo - -import ( - "testing" - - "github.com/stretchr/testify/assert" -) - -func TestToPtr(t *testing.T) { - t.Parallel() - is := assert.New(t) - - result1 := ToPtr([]int{1, 2}) - - is.Equal(*result1, []int{1, 2}) -} - -func TestEmptyableToPtr(t *testing.T) { - t.Parallel() - is := assert.New(t) - - is.Nil(EmptyableToPtr(0)) - is.Nil(EmptyableToPtr("")) - is.Nil(EmptyableToPtr[[]int](nil)) - is.Nil(EmptyableToPtr[map[int]int](nil)) - is.Nil(EmptyableToPtr[error](nil)) - - is.Equal(*EmptyableToPtr(42), 42) - is.Equal(*EmptyableToPtr("nonempty"), "nonempty") - is.Equal(*EmptyableToPtr([]int{}), []int{}) - is.Equal(*EmptyableToPtr([]int{1, 2}), []int{1, 2}) - is.Equal(*EmptyableToPtr(map[int]int{}), map[int]int{}) - is.Equal(*EmptyableToPtr(assert.AnError), assert.AnError) -} - -func TestFromPtr(t *testing.T) { - t.Parallel() - is := assert.New(t) - - str1 := "foo" - ptr := &str1 - - is.Equal("foo", FromPtr(ptr)) - is.Equal("", FromPtr[string](nil)) - is.Equal(0, FromPtr[int](nil)) - is.Nil(FromPtr[*string](nil)) - is.EqualValues(ptr, FromPtr(&ptr)) -} - -func TestFromPtrOr(t *testing.T) { - t.Parallel() - is := assert.New(t) - - const fallbackStr = "fallback" - str := "foo" - ptrStr := &str - - const fallbackInt = -1 - i := 9 - ptrInt := &i - - is.Equal(str, FromPtrOr(ptrStr, fallbackStr)) - is.Equal(fallbackStr, FromPtrOr(nil, fallbackStr)) - is.Equal(i, FromPtrOr(ptrInt, fallbackInt)) - is.Equal(fallbackInt, FromPtrOr(nil, fallbackInt)) -} - -func TestToSlicePtr(t *testing.T) { - t.Parallel() - is := assert.New(t) - - str1 := "foo" - str2 := "bar" - result1 := ToSlicePtr([]string{str1, str2}) - - is.Equal(result1, []*string{&str1, &str2}) -} - -func TestToAnySlice(t *testing.T) { - t.Parallel() - is := assert.New(t) - - in1 := []int{0, 1, 2, 3} - in2 := []int{} - out1 := ToAnySlice(in1) - out2 := ToAnySlice(in2) - - is.Equal([]any{0, 1, 2, 3}, out1) - is.Equal([]any{}, out2) -} - -func TestFromAnySlice(t *testing.T) { - t.Parallel() - is := assert.New(t) - - is.NotPanics(func() { - out1, ok1 := FromAnySlice[string]([]any{"foobar", 42}) - out2, ok2 := FromAnySlice[string]([]any{"foobar", "42"}) - - is.Equal([]string{}, out1) - is.False(ok1) - is.Equal([]string{"foobar", "42"}, out2) - is.True(ok2) - }) -} - -func TestEmpty(t *testing.T) { - t.Parallel() - is := assert.New(t) - - //nolint:unused - type test struct{} - - is.Empty(Empty[string]()) - is.Empty(Empty[int64]()) - is.Empty(Empty[test]()) - is.Empty(Empty[chan string]()) -} - -func TestIsEmpty(t *testing.T) { - t.Parallel() - is := assert.New(t) - - //nolint:unused - type test struct { - foobar string - } - - is.True(IsEmpty("")) - is.False(IsEmpty("foo")) - is.True(IsEmpty[int64](0)) - is.False(IsEmpty[int64](42)) - is.True(IsEmpty(test{foobar: ""})) - is.False(IsEmpty(test{foobar: "foo"})) -} - -func TestIsNotEmpty(t *testing.T) { - t.Parallel() - is := assert.New(t) - - //nolint:unused - type test struct { - foobar string - } - - is.False(IsNotEmpty("")) - is.True(IsNotEmpty("foo")) - is.False(IsNotEmpty[int64](0)) - is.True(IsNotEmpty[int64](42)) - is.False(IsNotEmpty(test{foobar: ""})) - is.True(IsNotEmpty(test{foobar: "foo"})) -} - -func TestCoalesce(t *testing.T) { - t.Parallel() - is := assert.New(t) - - newStr := func(v string) *string { return &v } - var nilStr *string - str1 := newStr("str1") - str2 := newStr("str2") - - type structType struct { - field1 int - field2 float64 - } - var zeroStruct structType - struct1 := structType{1, 1.0} - struct2 := structType{2, 2.0} - - result1, ok1 := Coalesce[int]() - result2, ok2 := Coalesce(3) - result3, ok3 := Coalesce(nil, nilStr) - result4, ok4 := Coalesce(nilStr, str1) - result5, ok5 := Coalesce(nilStr, str1, str2) - result6, ok6 := Coalesce(str1, str2, nilStr) - result7, ok7 := Coalesce(0, 1, 2, 3) - result8, ok8 := Coalesce(zeroStruct) - result9, ok9 := Coalesce(zeroStruct, struct1) - result10, ok10 := Coalesce(zeroStruct, struct1, struct2) - - is.Equal(0, result1) - is.False(ok1) - - is.Equal(3, result2) - is.True(ok2) - - is.Nil(result3) - is.False(ok3) - - is.Equal(str1, result4) - is.True(ok4) - - is.Equal(str1, result5) - is.True(ok5) - - is.Equal(str1, result6) - is.True(ok6) - - is.Equal(result7, 1) - is.True(ok7) - - is.Equal(result8, zeroStruct) - is.False(ok8) - - is.Equal(result9, struct1) - is.True(ok9) - - is.Equal(result10, struct1) - is.True(ok10) -}