1
0
mirror of https://github.com/duke-git/lancet.git synced 2026-02-15 02:02:27 +08:00

Merge branch 'rc'

This commit is contained in:
dudaodong
2024-11-19 10:26:41 +08:00
11 changed files with 628 additions and 127 deletions

View File

@@ -8,7 +8,7 @@ import (
func TestLRUCache(t *testing.T) { func TestLRUCache(t *testing.T) {
t.Parallel() t.Parallel()
asssert := internal.NewAssert(t, "TestLRUCache") assert := internal.NewAssert(t, "TestLRUCache")
cache := NewLRUCache[int, int](3) cache := NewLRUCache[int, int](3)
@@ -16,19 +16,19 @@ func TestLRUCache(t *testing.T) {
cache.Put(2, 2) cache.Put(2, 2)
cache.Put(3, 3) cache.Put(3, 3)
asssert.Equal(3, cache.Len()) assert.Equal(3, cache.Len())
v, ok := cache.Get(1) v, ok := cache.Get(1)
asssert.Equal(true, ok) assert.Equal(true, ok)
asssert.Equal(1, v) assert.Equal(1, v)
v, ok = cache.Get(2) v, ok = cache.Get(2)
asssert.Equal(true, ok) assert.Equal(true, ok)
asssert.Equal(2, v) assert.Equal(2, v)
ok = cache.Delete(2) ok = cache.Delete(2)
asssert.Equal(true, ok) assert.Equal(true, ok)
_, ok = cache.Get(2) _, ok = cache.Get(2)
asssert.Equal(false, ok) assert.Equal(false, ok)
} }

View File

@@ -8,34 +8,34 @@ import (
func TestLinearSearch(t *testing.T) { func TestLinearSearch(t *testing.T) {
t.Parallel() t.Parallel()
asssert := internal.NewAssert(t, "TestLinearSearch") assert := internal.NewAssert(t, "TestLinearSearch")
numbers := []int{3, 4, 5, 3, 2, 1} numbers := []int{3, 4, 5, 3, 2, 1}
equalFunc := func(a, b int) bool { equalFunc := func(a, b int) bool {
return a == b return a == b
} }
asssert.Equal(0, LinearSearch(numbers, 3, equalFunc)) assert.Equal(0, LinearSearch(numbers, 3, equalFunc))
asssert.Equal(-1, LinearSearch(numbers, 6, equalFunc)) assert.Equal(-1, LinearSearch(numbers, 6, equalFunc))
} }
func TestBinarySearch(t *testing.T) { func TestBinarySearch(t *testing.T) {
t.Parallel() t.Parallel()
asssert := internal.NewAssert(t, "TestBinarySearch") assert := internal.NewAssert(t, "TestBinarySearch")
sortedNumbers := []int{1, 2, 3, 4, 5, 6, 7, 8} sortedNumbers := []int{1, 2, 3, 4, 5, 6, 7, 8}
comparator := &intComparator{} comparator := &intComparator{}
asssert.Equal(4, BinarySearch(sortedNumbers, 5, 0, len(sortedNumbers)-1, comparator)) assert.Equal(4, BinarySearch(sortedNumbers, 5, 0, len(sortedNumbers)-1, comparator))
asssert.Equal(-1, BinarySearch(sortedNumbers, 9, 0, len(sortedNumbers)-1, comparator)) assert.Equal(-1, BinarySearch(sortedNumbers, 9, 0, len(sortedNumbers)-1, comparator))
} }
func TestBinaryIterativeSearch(t *testing.T) { func TestBinaryIterativeSearch(t *testing.T) {
asssert := internal.NewAssert(t, "TestBinaryIterativeSearch") assert := internal.NewAssert(t, "TestBinaryIterativeSearch")
sortedNumbers := []int{1, 2, 3, 4, 5, 6, 7, 8} sortedNumbers := []int{1, 2, 3, 4, 5, 6, 7, 8}
comparator := &intComparator{} comparator := &intComparator{}
asssert.Equal(4, BinaryIterativeSearch(sortedNumbers, 5, 0, len(sortedNumbers)-1, comparator)) assert.Equal(4, BinaryIterativeSearch(sortedNumbers, 5, 0, len(sortedNumbers)-1, comparator))
asssert.Equal(-1, BinaryIterativeSearch(sortedNumbers, 9, 0, len(sortedNumbers)-1, comparator)) assert.Equal(-1, BinaryIterativeSearch(sortedNumbers, 9, 0, len(sortedNumbers)-1, comparator))
} }

View File

@@ -47,7 +47,7 @@ func (c *intComparator) Compare(v1 any, v2 any) int {
func TestBubbleSortForStructSlice(t *testing.T) { func TestBubbleSortForStructSlice(t *testing.T) {
t.Parallel() t.Parallel()
asssert := internal.NewAssert(t, "TestBubbleSortForStructSlice") assert := internal.NewAssert(t, "TestBubbleSortForStructSlice")
peoples := []people{ peoples := []people{
{Name: "a", Age: 20}, {Name: "a", Age: 20},
@@ -62,23 +62,23 @@ func TestBubbleSortForStructSlice(t *testing.T) {
expected := "[{d 8} {b 10} {c 17} {a 20} {e 28}]" expected := "[{d 8} {b 10} {c 17} {a 20} {e 28}]"
actual := fmt.Sprintf("%v", peoples) actual := fmt.Sprintf("%v", peoples)
asssert.Equal(expected, actual) assert.Equal(expected, actual)
} }
func TestBubbleSortForIntSlice(t *testing.T) { func TestBubbleSortForIntSlice(t *testing.T) {
t.Parallel() t.Parallel()
asssert := internal.NewAssert(t, "TestBubbleSortForIntSlice") assert := internal.NewAssert(t, "TestBubbleSortForIntSlice")
numbers := []int{2, 1, 5, 3, 6, 4} numbers := []int{2, 1, 5, 3, 6, 4}
comparator := &intComparator{} comparator := &intComparator{}
BubbleSort(numbers, comparator) BubbleSort(numbers, comparator)
asssert.Equal([]int{1, 2, 3, 4, 5, 6}, numbers) assert.Equal([]int{1, 2, 3, 4, 5, 6}, numbers)
} }
func TestInsertionSort(t *testing.T) { func TestInsertionSort(t *testing.T) {
t.Parallel() t.Parallel()
asssert := internal.NewAssert(t, "TestInsertionSort") assert := internal.NewAssert(t, "TestInsertionSort")
peoples := []people{ peoples := []people{
{Name: "a", Age: 20}, {Name: "a", Age: 20},
@@ -93,12 +93,12 @@ func TestInsertionSort(t *testing.T) {
expected := "[{d 8} {b 10} {c 17} {a 20} {e 28}]" expected := "[{d 8} {b 10} {c 17} {a 20} {e 28}]"
actual := fmt.Sprintf("%v", peoples) actual := fmt.Sprintf("%v", peoples)
asssert.Equal(expected, actual) assert.Equal(expected, actual)
} }
func TestSelectionSort(t *testing.T) { func TestSelectionSort(t *testing.T) {
t.Parallel() t.Parallel()
asssert := internal.NewAssert(t, "TestSelectionSort") assert := internal.NewAssert(t, "TestSelectionSort")
peoples := []people{ peoples := []people{
{Name: "a", Age: 20}, {Name: "a", Age: 20},
@@ -113,12 +113,12 @@ func TestSelectionSort(t *testing.T) {
expected := "[{d 8} {b 10} {c 17} {a 20} {e 28}]" expected := "[{d 8} {b 10} {c 17} {a 20} {e 28}]"
actual := fmt.Sprintf("%v", peoples) actual := fmt.Sprintf("%v", peoples)
asssert.Equal(expected, actual) assert.Equal(expected, actual)
} }
func TestShellSort(t *testing.T) { func TestShellSort(t *testing.T) {
t.Parallel() t.Parallel()
asssert := internal.NewAssert(t, "TestShellSort") assert := internal.NewAssert(t, "TestShellSort")
peoples := []people{ peoples := []people{
{Name: "a", Age: 20}, {Name: "a", Age: 20},
@@ -133,12 +133,12 @@ func TestShellSort(t *testing.T) {
expected := "[{d 8} {b 10} {c 17} {a 20} {e 28}]" expected := "[{d 8} {b 10} {c 17} {a 20} {e 28}]"
actual := fmt.Sprintf("%v", peoples) actual := fmt.Sprintf("%v", peoples)
asssert.Equal(expected, actual) assert.Equal(expected, actual)
} }
func TestQuickSort(t *testing.T) { func TestQuickSort(t *testing.T) {
t.Parallel() t.Parallel()
asssert := internal.NewAssert(t, "TestQuickSort") assert := internal.NewAssert(t, "TestQuickSort")
peoples := []people{ peoples := []people{
{Name: "a", Age: 20}, {Name: "a", Age: 20},
@@ -153,12 +153,12 @@ func TestQuickSort(t *testing.T) {
expected := "[{d 8} {b 10} {c 17} {a 20} {e 28}]" expected := "[{d 8} {b 10} {c 17} {a 20} {e 28}]"
actual := fmt.Sprintf("%v", peoples) actual := fmt.Sprintf("%v", peoples)
asssert.Equal(expected, actual) assert.Equal(expected, actual)
} }
func TestHeapSort(t *testing.T) { func TestHeapSort(t *testing.T) {
t.Parallel() t.Parallel()
asssert := internal.NewAssert(t, "TestHeapSort") assert := internal.NewAssert(t, "TestHeapSort")
peoples := []people{ peoples := []people{
{Name: "a", Age: 20}, {Name: "a", Age: 20},
@@ -173,12 +173,12 @@ func TestHeapSort(t *testing.T) {
expected := "[{d 8} {b 10} {c 17} {a 20} {e 28}]" expected := "[{d 8} {b 10} {c 17} {a 20} {e 28}]"
actual := fmt.Sprintf("%v", peoples) actual := fmt.Sprintf("%v", peoples)
asssert.Equal(expected, actual) assert.Equal(expected, actual)
} }
func TestMergeSort(t *testing.T) { func TestMergeSort(t *testing.T) {
t.Parallel() t.Parallel()
asssert := internal.NewAssert(t, "TestMergeSort") assert := internal.NewAssert(t, "TestMergeSort")
peoples := []people{ peoples := []people{
{Name: "a", Age: 20}, {Name: "a", Age: 20},
@@ -193,12 +193,12 @@ func TestMergeSort(t *testing.T) {
expected := "[{d 8} {b 10} {c 17} {a 20} {e 28}]" expected := "[{d 8} {b 10} {c 17} {a 20} {e 28}]"
actual := fmt.Sprintf("%v", peoples) actual := fmt.Sprintf("%v", peoples)
asssert.Equal(expected, actual) assert.Equal(expected, actual)
} }
func TestCountSort(t *testing.T) { func TestCountSort(t *testing.T) {
t.Parallel() t.Parallel()
asssert := internal.NewAssert(t, "TestCountSort") assert := internal.NewAssert(t, "TestCountSort")
peoples := []people{ peoples := []people{
{Name: "a", Age: 20}, {Name: "a", Age: 20},
@@ -213,5 +213,5 @@ func TestCountSort(t *testing.T) {
expected := "[{d 8} {b 10} {c 17} {a 20} {e 28}]" expected := "[{d 8} {b 10} {c 17} {a 20} {e 28}]"
actual := fmt.Sprintf("%v", sortedPeopleByAge) actual := fmt.Sprintf("%v", sortedPeopleByAge)
asssert.Equal(expected, actual) assert.Equal(expected, actual)
} }

View File

@@ -1,51 +1,51 @@
-----BEGIN rsa private key----- -----BEGIN rsa private key-----
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
-----END rsa private key----- -----END rsa private key-----

View File

@@ -1,14 +1,14 @@
-----BEGIN rsa public key----- -----BEGIN rsa public key-----
MIICIjANBgkqhkiG9w0BAQEFAAOCAg8AMIICCgKCAgEA3bRSY5GD7uJB3jvwqa9Z MIICIjANBgkqhkiG9w0BAQEFAAOCAg8AMIICCgKCAgEAymvyNgI0T1P/DnFA2Fom
ZFpN3uLIGbbPA+yiyf6tJZp3K3rmkVFfEcWqtK1EfHvd9G4rqLYJ9ZcohDZgD/Ww Mrx4SzBf9p4VJ70AyYmbdeGhtzh+u6zNoDQ2UMmDzcCbtv9JW7PX80O8xy/O006g
mqJtaaWh2/7feMPaitp50bYVilpPhaxULx+MIjQn3XXowYvr4fX7N052t4IC95tA eNPfW74T5ryH2GEj3Y+eOtIzYI6gQy74JXqiqEztE6BkvesYHC+Yo8IIrawBBYHg
anPEEwZRQJOVMtibAxwI/ofUOCpTPtuK3AoErDxS18JPgjQ34yY4Jsch0de53+Sj GvluAudTZPqnkcqnUd8ngfhahCQrMi+sKqiqOWC/D0FVSclfugWw5/EBxJJSBSPY
Tk+bJpLUlnY4brm+A23FhwTlE5njrKA+Texrg52KJ8aPhLuVQBcZP1SJsxv2PZru umLJelbk3PqXtVm46mvGnlQlfHGppYQ5Nj6zKilCgoJoAHURp4dAaOwAhVOtc31M
uD+0xfLDRrZ7BOTpun+1FBhdlxBefIfBQbBBfy7STw+ignTaO+IRIHhcqKZ+12Na 0WPre/9th4TodZu1GeqFt5HqmMeP5+p2GDNDSxDNP3lgCgSqwRzy4pYaE5e70azn
+4GAusmpSiB3LATy82h0nB0PX3hSOLYmFI61px4l/yM50E4brF1NFtd/BpoozZaj Os5iaclAAlrLN3aSK6lDT+BGQbQrQgM47x3flMfszqNeuaBwdiNyzEodhT8eiYl8
gxjJaznuZXFQ1YSG0JjCeszqdzU+6dexGTr+4Lr87NfLekmUX1nZYy/E5lST65lG m08B1sVI811q7pG8WUVZjIYs2BzVjK/VDnvbEyayX+RGCAXr5M/bfDM1YRfVS9TW
lI4hX1nR5+nVN9ALRYByNz6oJd0IfF4dhoNlGPc1VksskeY8rPZwXITbSifAN7zv xspQNB3pyxgLX//LJIATbutUVKcrjxjoS7GdEocSruTOm/J+ZMTm0EqhsbRHVm+7
EiwKreFV3t0BLKsvWRu9GdpWy+d2AmelXkNm+QaH2mPM17euMoNZVyzizrZaJkh/ GcsSLaiSACEq+ONQJsN1x1o2GGVEi3pEZnDITSsokdcyrBj1A9a5Hx4tSiMbg88g
aHO/UgY1/y7sXFl4akC9hk9ILONCUn6FVI4BXMXb5kZgwDk5tWE5A159LtC579yG S4MPOALzBTmEVneQC+U5HTG/erUpZk6/AhT9Flk3HQTNIdzz8a2Clfeh4GU1JoKB
cnxyc9Y9NNFOGrqFqPiu6QUCAwEAAQ== 4u++XPt4M5h75OWnd5r9HYUCAwEAAQ==
-----END rsa public key----- -----END rsa public key-----

View File

@@ -33,7 +33,7 @@ import (
- [Percent](#Percent) - [Percent](#Percent)
- [RoundToFloat](#RoundToFloat) - [RoundToFloat](#RoundToFloat)
- [RoundToString](#RoundToString) - [RoundToString](#RoundToString)
- [TruncRound](#TruncRound) - [T运行cRound](#T运行cRound)
- [CeilToFloat](#CeilToFloat) - [CeilToFloat](#CeilToFloat)
- [CeilToString](#CeilToString) - [CeilToString](#CeilToString)
- [FloorToFloat](#FloorToFloat) - [FloorToFloat](#FloorToFloat)
@@ -52,6 +52,10 @@ import (
- [Sum](#Sum) - [Sum](#Sum)
- [Abs](#Abs) - [Abs](#Abs)
- [Div](#Div) - [Div](#Div)
- [Variance](#Variance)
- [StdDev](#StdDev)
- [Permutation](#Permutation)
- [Combination](#Combination)
<div STYLE="page-break-after: always;"></div> <div STYLE="page-break-after: always;"></div>
@@ -64,7 +68,7 @@ import (
<b>函数签名:</b> <b>函数签名:</b>
```go ```go
func Average[T constraints.Integer | constraints.Float](numbers ...T) T func Average[T constraints.Integer | constraints.Float](numbers ...T) float64
``` ```
<b>示例:<span style="float:right;display:inline-block;">[运行](https://go.dev/play/p/HFd70x4DrMj)</span></b> <b>示例:<span style="float:right;display:inline-block;">[运行](https://go.dev/play/p/HFd70x4DrMj)</span></b>
@@ -87,7 +91,7 @@ func main() {
fmt.Println(result2) fmt.Println(result2)
// Output: // Output:
// 1 // 1.5
// 1.3 // 1.3
} }
``` ```
@@ -462,14 +466,14 @@ func main() {
} }
``` ```
### <span id="TruncRound">TruncRound</span> ### <span id="T运行cRound">T运行cRound</span>
<p>截短n位小数不进行四舍五入</p> <p>截短n位小数不进行四舍五入</p>
<b>函数签名:</b> <b>函数签名:</b>
```go ```go
func TruncRound[T constraints.Float | constraints.Integer](x T, n int) T func T运行cRound[T constraints.Float | constraints.Integer](x T, n int) T
``` ```
<b>示例:<span style="float:right;display:inline-block;">[运行](https://go.dev/play/p/aumarSHIGzP)</span></b> <b>示例:<span style="float:right;display:inline-block;">[运行](https://go.dev/play/p/aumarSHIGzP)</span></b>
@@ -483,9 +487,9 @@ import (
) )
func main() { func main() {
result1 := mathutil.TruncRound(0.124, 2) result1 := mathutil.T运行cRound(0.124, 2)
result2 := mathutil.TruncRound(0.125, 2) result2 := mathutil.T运行cRound(0.125, 2)
result3 := mathutil.TruncRound(0.125, 3) result3 := mathutil.T运行cRound(0.125, 3)
fmt.Println(result1) fmt.Println(result1)
fmt.Println(result2) fmt.Println(result2)
@@ -1045,8 +1049,8 @@ import (
func main() { func main() {
result1 := mathutil.Log(8, 2) result1 := mathutil.Log(8, 2)
result2 := mathutil.TruncRound(mathutil.Log(5, 2), 2) result2 := mathutil.T运行cRound(mathutil.Log(5, 2), 2)
result3 := mathutil.TruncRound(mathutil.Log(27, 3), 0) result3 := mathutil.T运行cRound(mathutil.Log(27, 3), 0)
fmt.Println(result1) fmt.Println(result1)
fmt.Println(result2) fmt.Println(result2)
@@ -1162,4 +1166,136 @@ func main() {
// 0.5 // 0.5
// 0 // 0
} }
```
### <span id="Variance">Variance</span>
<p>计算方差。</p>
<b>函数签名:</b>
```go
func Variance[T constraints.Float | constraints.Integer](numbers []T) float64
```
<b>示例:<span style="float:right;display:inline-block;">[示例](todo)</span></b>
```go
package main
import (
"fmt"
"github.com/duke-git/lancet/v2/mathutil"
)
func main() {
result1 := mathutil.Variance([]int{1, 2, 3, 4, 5})
result2 := mathutil.Variance([]float64{1.1, 2.2, 3.3, 4.4, 5.5})
fmt.Println(result1)
fmt.Println(result2)
// Output:
// 2
// 2.42
}
```
### <span id="StdDev">StdDev</span>
<p>计算标准差。</p>
<b>函数签名:</b>
```go
func StdDev[T constraints.Float | constraints.Integer](numbers []T) float64
```
<b>示例:<span style="float:right;display:inline-block;">[运行](todo)</span></b>
```go
package main
import (
"fmt"
"github.com/duke-git/lancet/v2/mathutil"
)
func main() {
result1 := mathutil.T运行cRound(mathutil.StdDev([]int{1, 2, 3, 4, 5}), 2)
result2 := mathutil.T运行cRound(mathutil.StdDev([]float64{1.1, 2.2, 3.3, 4.4, 5.5}), 2)
fmt.Println(result1)
fmt.Println(result2)
// Output:
// 1.41
// 1.55
}
```
### <span id="Permutation">Permutation</span>
<p>计算排列数P(n, k))。</p>
<b>函数签名:</b>
```go
func Permutation(n, k uint) uint
```
<b>示例:<span style="float:right;display:inline-block;">[运行](todo)</span></b>
```go
package main
import (
"fmt"
"github.com/duke-git/lancet/v2/mathutil"
)
func main() {
result1 := mathutil.Permutation(5, 3)
result2 := mathutil.Permutation(5, 5)
fmt.Println(result1)
fmt.Println(result2)
// Output:
// 60
// 120
}
```
### <span id="Combination">Combination</span>
<p>计算组合数C(n, k))。</p>
<b>函数签名:</b>
```go
func Combination(n, k uint) uint
```
<b>示例:<span style="float:right;display:inline-block;">[运行](todo)</span></b>
```go
package main
import (
"fmt"
"github.com/duke-git/lancet/v2/mathutil"
)
func main() {
result1 := mathutil.Combination(5, 3)
result2 := mathutil.Combination(5, 5)
fmt.Println(result1)
fmt.Println(result2)
// Output:
// 10
// 1
}
``` ```

View File

@@ -52,6 +52,10 @@ import (
- [Sum](#Sum) - [Sum](#Sum)
- [Abs](#Abs) - [Abs](#Abs)
- [Div](#Div) - [Div](#Div)
- [Variance](#Variance)
- [StdDev](#StdDev)
- [Permutation](#Permutation)
- [Combination](#Combination)
<div STYLE="page-break-after: always;"></div> <div STYLE="page-break-after: always;"></div>
@@ -64,7 +68,7 @@ import (
<b>Signature:</b> <b>Signature:</b>
```go ```go
func Average[T constraints.Integer | constraints.Float](numbers ...T) T func Average[T constraints.Integer | constraints.Float](numbers ...T) float64
``` ```
<b>Example:<span style="float:right;display:inline-block;">[Run](https://go.dev/play/p/Vv7LBwER-pz)</span></b> <b>Example:<span style="float:right;display:inline-block;">[Run](https://go.dev/play/p/Vv7LBwER-pz)</span></b>
@@ -87,7 +91,7 @@ func main() {
fmt.Println(result2) fmt.Println(result2)
// Output: // Output:
// 1 // 1.5
// 1.3 // 1.3
} }
``` ```
@@ -1161,4 +1165,136 @@ func main() {
// 0.5 // 0.5
// 0 // 0
} }
```
### <span id="Variance">Variance</span>
<p>Returns the variance of numbers.</p>
<b>Signature:</b>
```go
func Variance[T constraints.Float | constraints.Integer](numbers []T) float64
```
<b>Example:<span style="float:right;display:inline-block;">[Run](todo)</span></b>
```go
package main
import (
"fmt"
"github.com/duke-git/lancet/v2/mathutil"
)
func main() {
result1 := mathutil.Variance([]int{1, 2, 3, 4, 5})
result2 := mathutil.Variance([]float64{1.1, 2.2, 3.3, 4.4, 5.5})
fmt.Println(result1)
fmt.Println(result2)
// Output:
// 2
// 2.42
}
```
### <span id="StdDev">StdDev</span>
<p>Returns the standard deviation of numbers.</p>
<b>Signature:</b>
```go
func StdDev[T constraints.Float | constraints.Integer](numbers []T) float64
```
<b>Example:<span style="float:right;display:inline-block;">[Run](todo)</span></b>
```go
package main
import (
"fmt"
"github.com/duke-git/lancet/v2/mathutil"
)
func main() {
result1 := mathutil.TruncRound(mathutil.StdDev([]int{1, 2, 3, 4, 5}), 2)
result2 := mathutil.TruncRound(mathutil.StdDev([]float64{1.1, 2.2, 3.3, 4.4, 5.5}), 2)
fmt.Println(result1)
fmt.Println(result2)
// Output:
// 1.41
// 1.55
}
```
### <span id="Permutation">Permutation</span>
<p>Calculates P(n, k).</p>
<b>Signature:</b>
```go
func Permutation(n, k uint) uint
```
<b>Example:<span style="float:right;display:inline-block;">[Run](todo)</span></b>
```go
package main
import (
"fmt"
"github.com/duke-git/lancet/v2/mathutil"
)
func main() {
result1 := mathutil.Permutation(5, 3)
result2 := mathutil.Permutation(5, 5)
fmt.Println(result1)
fmt.Println(result2)
// Output:
// 60
// 120
}
```
### <span id="Combination">Combination</span>
<p>Calculates C(n, k).</p>
<b>Signature:</b>
```go
func Combination(n, k uint) uint
```
<b>Example:<span style="float:right;display:inline-block;">[Run](todo)</span></b>
```go
package main
import (
"fmt"
"github.com/duke-git/lancet/v2/mathutil"
)
func main() {
result1 := mathutil.Combination(5, 3)
result2 := mathutil.Combination(5, 5)
fmt.Println(result1)
fmt.Println(result2)
// Output:
// 10
// 1
}
``` ```

View File

@@ -44,14 +44,19 @@ func Fibonacci(first, second, n int) int {
} }
} }
// Factorial calculate x!. // Factorial calculate n!.
// Play: https://go.dev/play/p/tt6LdOK67Nx // Play: https://go.dev/play/p/tt6LdOK67Nx
func Factorial(x uint) uint { func Factorial(n uint) uint {
var f uint = 1 if n == 0 || n == 1 {
for ; x > 1; x-- { return 1
f *= x
} }
return f
result := uint(1)
for i := uint(2); i <= n; i++ {
result *= i
}
return result
} }
// Percent calculate the percentage of value to total. // Percent calculate the percentage of value to total.
@@ -224,14 +229,12 @@ func Sum[T constraints.Integer | constraints.Float](numbers ...T) T {
// Average return average value of numbers. // Average return average value of numbers.
// Play: https://go.dev/play/p/Vv7LBwER-pz // Play: https://go.dev/play/p/Vv7LBwER-pz
func Average[T constraints.Integer | constraints.Float](numbers ...T) T { func Average[T constraints.Integer | constraints.Float](numbers ...T) float64 {
var sum T var sum float64
n := T(len(numbers)) for _, num := range numbers {
sum += float64(num)
for _, v := range numbers {
sum += v
} }
return sum / n return sum / float64(len(numbers))
} }
// Range creates a slice of numbers from start with specified count, element step is 1. // Range creates a slice of numbers from start with specified count, element step is 1.
@@ -395,3 +398,54 @@ func Abs[T constraints.Integer | constraints.Float](x T) T {
func Div[T constraints.Float | constraints.Integer](x T, y T) float64 { func Div[T constraints.Float | constraints.Integer](x T, y T) float64 {
return float64(x) / float64(y) return float64(x) / float64(y)
} }
// Variance returns the variance of numbers.
// Play: todo
func Variance[T constraints.Float | constraints.Integer](numbers []T) float64 {
n := len(numbers)
if n == 0 {
return 0
}
avg := Average(numbers...)
var sum float64
for _, v := range numbers {
sum += (float64(v) - avg) * (float64(v) - avg)
}
return sum / float64(n)
}
// StdDev returns the standard deviation of numbers.
// Play: todo
func StdDev[T constraints.Float | constraints.Integer](numbers []T) float64 {
return math.Sqrt(Variance(numbers))
}
// Permutation calculate P(n, k).
// Play: todo
func Permutation(n, k uint) uint {
if n < k {
return 0
}
nFactorial := Factorial(n)
nMinusKFactorial := Factorial(n - k)
return nFactorial / nMinusKFactorial
}
// Combination calculate C(n, k).
// Play: todo
func Combination(n, k uint) uint {
if n < k {
return 0
}
nFactorial := Factorial(n)
kFactorial := Factorial(k)
nMinusKFactorial := Factorial(n - k)
return nFactorial / (kFactorial * nMinusKFactorial)
}

View File

@@ -178,7 +178,7 @@ func ExampleAverage() {
fmt.Println(result2) fmt.Println(result2)
// Output: // Output:
// 1 // 1.5
// 1.3 // 1.3
} }
@@ -478,3 +478,51 @@ func ExampleDiv() {
// 0.5 // 0.5
// 0 // 0
} }
func ExampleVariance() {
result1 := Variance([]int{1, 2, 3, 4, 5})
result2 := Variance([]float64{1.1, 2.2, 3.3, 4.4, 5.5})
fmt.Println(result1)
fmt.Println(result2)
// Output:
// 2
// 2.42
}
func ExampleStdDev() {
result1 := TruncRound(StdDev([]int{1, 2, 3, 4, 5}), 2)
result2 := TruncRound(StdDev([]float64{1.1, 2.2, 3.3, 4.4, 5.5}), 2)
fmt.Println(result1)
fmt.Println(result2)
// Output:
// 1.41
// 1.55
}
func ExamplePermutation() {
result1 := Permutation(5, 3)
result2 := Permutation(5, 5)
fmt.Println(result1)
fmt.Println(result2)
// Output:
// 60
// 120
}
func ExampleCombination() {
result1 := Combination(5, 3)
result2 := Combination(5, 5)
fmt.Println(result1)
fmt.Println(result2)
// Output:
// 10
// 1
}

View File

@@ -143,11 +143,22 @@ func TestAverage(t *testing.T) {
assert := internal.NewAssert(t, "TestAverage") assert := internal.NewAssert(t, "TestAverage")
assert.Equal(0, Average(0, 0)) tests := []struct {
assert.Equal(1, Average(1, 1)) numbers []int
expected float64
}{
{[]int{0}, 0},
{[]int{1, 1, 1}, 1},
{[]int{1, 2, 3, 4}, 2.5},
{[]int{1, 2, 3, 4, 5}, 3},
}
avg := Average(1.2, 1.4) for _, tt := range tests {
assert.Equal(1.3, RoundToFloat(avg, 1)) assert.Equal(tt.expected, Average(tt.numbers...))
}
avg := Average(1.1, 1.2, 1.3, 1.4)
assert.Equal(1.25, avg)
} }
func TestSum(t *testing.T) { func TestSum(t *testing.T) {
@@ -413,3 +424,116 @@ func TestDiv(t *testing.T) {
assert.Equal(math.Inf(-1), Div(-8, 0)) assert.Equal(math.Inf(-1), Div(-8, 0))
assert.Equal(true, math.IsNaN(Div(0, 0))) assert.Equal(true, math.IsNaN(Div(0, 0)))
} }
func TestVariance(t *testing.T) {
t.Parallel()
assert := internal.NewAssert(t, "TestVariance")
testIntNumbers := []struct {
numbers []int
expected float64
}{
{[]int{0}, 0},
{[]int{1, 1, 1}, 0},
{[]int{1, 2, 3, 4}, 1.25},
{[]int{1, 2, 3, 4, 5}, 2.0},
}
for _, tt := range testIntNumbers {
assert.Equal(tt.expected, TruncRound(Variance(tt.numbers), 2))
}
testFloatNumbers := []struct {
numbers []float64
expected float64
}{
{[]float64{0}, 0},
{[]float64{1, 1, 1}, 0},
{[]float64{1.1, 2.2, 3.3, 4.4}, 1.51},
}
for _, tt := range testFloatNumbers {
assert.Equal(tt.expected, TruncRound(Variance(tt.numbers), 2))
}
}
func TestStdDev(t *testing.T) {
t.Parallel()
assert := internal.NewAssert(t, "TestStdDev")
testIntNumbers := []struct {
numbers []int
expected float64
}{
{[]int{0}, 0},
{[]int{1, 1, 1}, 0},
{[]int{1, 2, 3, 4}, 1.118},
{[]int{1, 2, 3, 4, 5}, 1.414},
}
for _, tt := range testIntNumbers {
assert.Equal(tt.expected, TruncRound(StdDev(tt.numbers), 3))
}
testFloatNumbers := []struct {
numbers []float64
expected float64
}{
{[]float64{0}, 0},
{[]float64{1, 1, 1}, 0},
{[]float64{1.1, 2.2, 3.3, 4.4}, 1.229},
}
for _, tt := range testFloatNumbers {
assert.Equal(tt.expected, TruncRound(StdDev(tt.numbers), 3))
}
}
func TestPermutation(t *testing.T) {
t.Parallel()
assert := internal.NewAssert(t, "TestPermutation")
tests := []struct {
n uint
k uint
expected uint
}{
{1, 1, 1},
{1, 0, 1},
{0, 1, 0},
{0, 0, 1},
{3, 2, 6},
{4, 2, 12},
}
for _, tt := range tests {
assert.Equal(tt.expected, Permutation(tt.n, tt.k))
}
}
func TestCombination(t *testing.T) {
t.Parallel()
assert := internal.NewAssert(t, "TestCombination")
tests := []struct {
n uint
k uint
expected uint
}{
{1, 1, 1},
{1, 0, 1},
{0, 1, 0},
{0, 0, 1},
{3, 2, 3},
{4, 2, 6},
}
for _, tt := range tests {
assert.Equal(tt.expected, Combination(tt.n, tt.k))
}
}

View File

@@ -10,6 +10,7 @@ import (
"io" "io"
"math" "math"
"math/rand" "math/rand"
"os"
"time" "time"
"unsafe" "unsafe"
@@ -274,7 +275,9 @@ func nearestPowerOfTwo(cap int) int {
// random generate a random string based on given string range. // random generate a random string based on given string range.
func random(s string, length int) string { func random(s string, length int) string {
// 确保随机数生成器的种子是动态的 // 确保随机数生成器的种子是动态的
rand.Seed(time.Now().UnixNano()) pid := os.Getpid()
timestamp := time.Now().UnixNano()
rand.Seed(int64(pid) + timestamp)
// 仿照strings.Builder // 仿照strings.Builder
// 创建一个长度为 length 的字节切片 // 创建一个长度为 length 的字节切片