github.com/linapex/ethereum-dpos-chinese@v0.0.0-20190316121959-b78b3a4a1ece/common/math/integer.go (about) 1 2 //<developer> 3 // <name>linapex 曹一峰</name> 4 // <email>linapex@163.com</email> 5 // <wx>superexc</wx> 6 // <qqgroup>128148617</qqgroup> 7 // <url>https://jsq.ink</url> 8 // <role>pku engineer</role> 9 // <date>2019-03-16 12:09:32</date> 10 //</624342609615130624> 11 12 13 package math 14 15 import ( 16 "fmt" 17 "strconv" 18 ) 19 20 //整数限制值。 21 const ( 22 MaxInt8 = 1<<7 - 1 23 MinInt8 = -1 << 7 24 MaxInt16 = 1<<15 - 1 25 MinInt16 = -1 << 15 26 MaxInt32 = 1<<31 - 1 27 MinInt32 = -1 << 31 28 MaxInt64 = 1<<63 - 1 29 MinInt64 = -1 << 63 30 MaxUint8 = 1<<8 - 1 31 MaxUint16 = 1<<16 - 1 32 MaxUint32 = 1<<32 - 1 33 MaxUint64 = 1<<64 - 1 34 ) 35 36 //hexordecimal64将uint64封送为十六进制或十进制。 37 type HexOrDecimal64 uint64 38 39 //UnmarshalText实现encoding.textUnmarshaller。 40 func (i *HexOrDecimal64) UnmarshalText(input []byte) error { 41 int, ok := ParseUint64(string(input)) 42 if !ok { 43 return fmt.Errorf("invalid hex or decimal integer %q", input) 44 } 45 *i = HexOrDecimal64(int) 46 return nil 47 } 48 49 //MarshalText实现Encoding.TextMarshaler。 50 func (i HexOrDecimal64) MarshalText() ([]byte, error) { 51 return []byte(fmt.Sprintf("%#x", uint64(i))), nil 52 } 53 54 //ParseUInt64以十进制或十六进制语法解析为整数。 55 //可接受前导零。空字符串解析为零。 56 func ParseUint64(s string) (uint64, bool) { 57 if s == "" { 58 return 0, true 59 } 60 if len(s) >= 2 && (s[:2] == "0x" || s[:2] == "0X") { 61 v, err := strconv.ParseUint(s[2:], 16, 64) 62 return v, err == nil 63 } 64 v, err := strconv.ParseUint(s, 10, 64) 65 return v, err == nil 66 } 67 68 //mustParseUInt64作为整数进行分析,如果字符串无效,则会恐慌。 69 func MustParseUint64(s string) uint64 { 70 v, ok := ParseUint64(s) 71 if !ok { 72 panic("invalid unsigned 64 bit integer: " + s) 73 } 74 return v 75 } 76 77 //注意:以下方法需要使用位检查或ASM进行优化 78 79 //SAFESUB返回减法结果以及是否发生溢出。 80 func SafeSub(x, y uint64) (uint64, bool) { 81 return x - y, x < y 82 } 83 84 //safeadd返回结果以及是否发生溢出。 85 func SafeAdd(x, y uint64) (uint64, bool) { 86 return x + y, y > MaxUint64-x 87 } 88 89 //safemul返回乘法结果以及是否发生溢出。 90 func SafeMul(x, y uint64) (uint64, bool) { 91 if x == 0 || y == 0 { 92 return 0, false 93 } 94 return x * y, y > MaxUint64/x 95 } 96