mirror of
https://github.com/go-sylixos/elvish.git
synced 2024-12-05 03:17:50 +08:00
Implement Hash for *big.Int and *big.Rat.
This commit is contained in:
parent
4afab8804b
commit
a12e1be189
|
@ -2,6 +2,7 @@ package vals
|
|||
|
||||
import (
|
||||
"math"
|
||||
"math/big"
|
||||
"reflect"
|
||||
|
||||
"src.elv.sh/pkg/persistent/hash"
|
||||
|
@ -24,7 +25,16 @@ func Hash(v interface{}) uint32 {
|
|||
return 1
|
||||
}
|
||||
return 0
|
||||
// TODO: Add support for the other num types: int, *big.Int, *big.Rat.
|
||||
case int:
|
||||
return hash.UIntPtr(uintptr(v))
|
||||
case *big.Int:
|
||||
h := hash.DJBCombine(hash.DJBInit, uint32(v.Sign()))
|
||||
for _, word := range v.Bits() {
|
||||
h = hash.DJBCombine(h, hash.UIntPtr(uintptr(word)))
|
||||
}
|
||||
return h
|
||||
case *big.Rat:
|
||||
return hash.DJB(Hash(v.Num()), Hash(v.Denom()))
|
||||
case float64:
|
||||
return hash.UInt64(math.Float64bits(v))
|
||||
case string:
|
||||
|
|
|
@ -2,8 +2,10 @@ package vals
|
|||
|
||||
import (
|
||||
"math"
|
||||
"math/big"
|
||||
"os"
|
||||
"testing"
|
||||
"unsafe"
|
||||
|
||||
"src.elv.sh/pkg/persistent/hash"
|
||||
. "src.elv.sh/pkg/tt"
|
||||
|
@ -16,9 +18,17 @@ func (hasher) Hash() uint32 { return 42 }
|
|||
type nonHasher struct{}
|
||||
|
||||
func TestHash(t *testing.T) {
|
||||
z := big.NewInt(5)
|
||||
z.Lsh(z, 8*uint(unsafe.Sizeof(int(0))))
|
||||
z.Add(z, big.NewInt(9))
|
||||
// z = 5 << wordSize + 9
|
||||
|
||||
Test(t, Fn("Hash", Hash), Table{
|
||||
Args(false).Rets(uint32(0)),
|
||||
Args(true).Rets(uint32(1)),
|
||||
Args(1).Rets(uint32(1)),
|
||||
Args(z).Rets(hash.DJB(1, 9, 5)),
|
||||
Args(big.NewRat(3, 2)).Rets(hash.DJB(Hash(big.NewInt(3)), Hash(big.NewInt(2)))),
|
||||
Args(1.0).Rets(hash.UInt64(math.Float64bits(1.0))),
|
||||
Args("foo").Rets(hash.String("foo")),
|
||||
Args(os.Stdin).Rets(hash.UIntPtr(os.Stdin.Fd())),
|
||||
|
|
Loading…
Reference in New Issue
Block a user