forked from zyedidia/generic
-
Notifications
You must be signed in to change notification settings - Fork 0
/
Copy pathgeneric.go
120 lines (106 loc) · 2.24 KB
/
generic.go
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
package generic
import (
"golang.org/x/exp/constraints"
"github.com/segmentio/fasthash/fnv1a"
)
// EqualsFn is a function that returns whether 'a' and 'b' are equal.
type EqualsFn[T any] func(a, b T) bool
// LessFn is a function that returns whether 'a' is less than 'b'.
type LessFn[T any] func(a, b T) bool
// HashFn is a function that returns the hash of 't'.
type HashFn[T any] func(t T) uint64
// Equals wraps the '==' operator for comparable types.
func Equals[T comparable](a, b T) bool {
return a == b
}
// Less wraps the '<' operator for ordered types.
func Less[T constraints.Ordered](a, b T) bool {
return a < b
}
// Compare uses a less function to determine the ordering of 'a' and 'b'. It returns:
//
// * -1 if a < b
//
// * 1 if a > b
//
// * 0 if a == b
func Compare[T any](a, b T, less LessFn[T]) int {
if less(a, b) {
return -1
} else if less(b, a) {
return 1
}
return 0
}
// Max returns the max of a and b.
func Max[T constraints.Ordered](a, b T) T {
if a > b {
return a
}
return b
}
// Min returns the min of a and b.
func Min[T constraints.Ordered](a, b T) T {
if a < b {
return a
}
return b
}
// MaxFunc returns the max of a and b using the less func.
func MaxFunc[T any](a, b T, less LessFn[T]) T {
if less(b, a) {
return a
}
return b
}
// MinFunc returns the min of a and b using the less func.
func MinFunc[T any](a, b T, less LessFn[T]) T {
if less(a, b) {
return a
}
return b
}
func HashUint64(u uint64) uint64 {
return hash(u)
}
func HashUint32(u uint32) uint64 {
return hash(uint64(u))
}
func HashUint16(u uint16) uint64 {
return hash(uint64(u))
}
func HashUint8(u uint8) uint64 {
return hash(uint64(u))
}
func HashInt64(i int64) uint64 {
return hash(uint64(i))
}
func HashInt32(i int32) uint64 {
return hash(uint64(i))
}
func HashInt16(i int16) uint64 {
return hash(uint64(i))
}
func HashInt8(i int8) uint64 {
return hash(uint64(i))
}
func HashInt(i int) uint64 {
return hash(uint64(i))
}
func HashUint(i uint) uint64 {
return hash(uint64(i))
}
func HashString(s string) uint64 {
return fnv1a.HashString64(s)
}
func HashBytes(b []byte) uint64 {
return fnv1a.HashBytes64(b)
}
func hash(u uint64) uint64 {
u ^= u >> 33
u *= 0xff51afd7ed558ccd
u ^= u >> 33
u *= 0xc4ceb9fe1a85ec53
u ^= u >> 33
return u
}