Merge pull request #1594 from ebuchman/trie_hex_fix
faster hex-prefix codec and string -> []byte
This commit is contained in:
		
						commit
						7baa5977c8
					
				| @ -18,11 +18,9 @@ package trie | ||||
| 
 | ||||
| import ( | ||||
| 	"bytes" | ||||
| 	"encoding/hex" | ||||
| 	"strings" | ||||
| ) | ||||
| 
 | ||||
| func CompactEncode(hexSlice []byte) string { | ||||
| func CompactEncode(hexSlice []byte) []byte { | ||||
| 	terminator := 0 | ||||
| 	if hexSlice[len(hexSlice)-1] == 16 { | ||||
| 		terminator = 1 | ||||
| @ -45,10 +43,10 @@ func CompactEncode(hexSlice []byte) string { | ||||
| 		buff.WriteByte(byte(16*hexSlice[i] + hexSlice[i+1])) | ||||
| 	} | ||||
| 
 | ||||
| 	return buff.String() | ||||
| 	return buff.Bytes() | ||||
| } | ||||
| 
 | ||||
| func CompactDecode(str string) []byte { | ||||
| func CompactDecode(str []byte) []byte { | ||||
| 	base := CompactHexDecode(str) | ||||
| 	base = base[:len(base)-1] | ||||
| 	if base[0] >= 2 { | ||||
| @ -63,30 +61,23 @@ func CompactDecode(str string) []byte { | ||||
| 	return base | ||||
| } | ||||
| 
 | ||||
| func CompactHexDecode(str string) []byte { | ||||
| 	base := "0123456789abcdef" | ||||
| 	var hexSlice []byte | ||||
| func CompactHexDecode(str []byte) []byte { | ||||
| 	var nibbles []byte | ||||
| 
 | ||||
| 	enc := hex.EncodeToString([]byte(str)) | ||||
| 	for _, v := range enc { | ||||
| 		hexSlice = append(hexSlice, byte(strings.IndexByte(base, byte(v)))) | ||||
| 	for _, b := range str { | ||||
| 		nibbles = append(nibbles, b/16) | ||||
| 		nibbles = append(nibbles, b%16) | ||||
| 	} | ||||
| 	hexSlice = append(hexSlice, 16) | ||||
| 
 | ||||
| 	return hexSlice | ||||
| 	nibbles = append(nibbles, 16) | ||||
| 	return nibbles | ||||
| } | ||||
| 
 | ||||
| func DecodeCompact(key []byte) string { | ||||
| 	const base = "0123456789abcdef" | ||||
| 	var str string | ||||
| 
 | ||||
| 	for _, v := range key { | ||||
| 		if v < 16 { | ||||
| 			str += string(base[v]) | ||||
| 		} | ||||
| // assumes key is odd length
 | ||||
| func DecodeCompact(key []byte) []byte { | ||||
| 	var res []byte | ||||
| 	for i := 0; i < len(key)-1; i += 2 { | ||||
| 		v1, v0 := key[i], key[i+1] | ||||
| 		res = append(res, v1*16+v0) | ||||
| 	} | ||||
| 
 | ||||
| 	res, _ := hex.DecodeString(str) | ||||
| 
 | ||||
| 	return string(res) | ||||
| 	return res | ||||
| } | ||||
|  | ||||
| @ -48,28 +48,28 @@ func (s *TrieEncodingSuite) TestCompactEncode(c *checker.C) { | ||||
| 
 | ||||
| func (s *TrieEncodingSuite) TestCompactHexDecode(c *checker.C) { | ||||
| 	exp := []byte{7, 6, 6, 5, 7, 2, 6, 2, 16} | ||||
| 	res := CompactHexDecode("verb") | ||||
| 	res := CompactHexDecode([]byte("verb")) | ||||
| 	c.Assert(res, checker.DeepEquals, exp) | ||||
| } | ||||
| 
 | ||||
| func (s *TrieEncodingSuite) TestCompactDecode(c *checker.C) { | ||||
| 	// odd compact decode
 | ||||
| 	exp := []byte{1, 2, 3, 4, 5} | ||||
| 	res := CompactDecode("\x11\x23\x45") | ||||
| 	res := CompactDecode([]byte("\x11\x23\x45")) | ||||
| 	c.Assert(res, checker.DeepEquals, exp) | ||||
| 
 | ||||
| 	// even compact decode
 | ||||
| 	exp = []byte{0, 1, 2, 3, 4, 5} | ||||
| 	res = CompactDecode("\x00\x01\x23\x45") | ||||
| 	res = CompactDecode([]byte("\x00\x01\x23\x45")) | ||||
| 	c.Assert(res, checker.DeepEquals, exp) | ||||
| 
 | ||||
| 	// even terminated compact decode
 | ||||
| 	exp = []byte{0, 15, 1, 12, 11, 8 /*term*/, 16} | ||||
| 	res = CompactDecode("\x20\x0f\x1c\xb8") | ||||
| 	res = CompactDecode([]byte("\x20\x0f\x1c\xb8")) | ||||
| 	c.Assert(res, checker.DeepEquals, exp) | ||||
| 
 | ||||
| 	// even terminated compact decode
 | ||||
| 	exp = []byte{15, 1, 12, 11, 8 /*term*/, 16} | ||||
| 	res = CompactDecode("\x3f\x1c\xb8") | ||||
| 	res = CompactDecode([]byte("\x3f\x1c\xb8")) | ||||
| 	c.Assert(res, checker.DeepEquals, exp) | ||||
| } | ||||
|  | ||||
| @ -41,7 +41,7 @@ func (self *Iterator) Next() bool { | ||||
| 		self.Key = make([]byte, 32) | ||||
| 	} | ||||
| 
 | ||||
| 	key := RemTerm(CompactHexDecode(string(self.Key))) | ||||
| 	key := RemTerm(CompactHexDecode(self.Key)) | ||||
| 	k := self.next(self.trie.root, key, isIterStart) | ||||
| 
 | ||||
| 	self.Key = []byte(DecodeCompact(k)) | ||||
|  | ||||
| @ -26,7 +26,7 @@ type ShortNode struct { | ||||
| } | ||||
| 
 | ||||
| func NewShortNode(t *Trie, key []byte, value Node) *ShortNode { | ||||
| 	return &ShortNode{t, []byte(CompactEncode(key)), value, false} | ||||
| 	return &ShortNode{t, CompactEncode(key), value, false} | ||||
| } | ||||
| func (self *ShortNode) Value() Node { | ||||
| 	self.value = self.trie.trans(self.value) | ||||
| @ -49,7 +49,7 @@ func (self *ShortNode) Hash() interface{} { | ||||
| } | ||||
| 
 | ||||
| func (self *ShortNode) Key() []byte { | ||||
| 	return CompactDecode(string(self.key)) | ||||
| 	return CompactDecode(self.key) | ||||
| } | ||||
| 
 | ||||
| func (self *ShortNode) setDirty(dirty bool) { | ||||
|  | ||||
							
								
								
									
										10
									
								
								trie/trie.go
									
									
									
									
									
								
							
							
						
						
									
										10
									
								
								trie/trie.go
									
									
									
									
									
								
							| @ -69,7 +69,7 @@ func (self *Trie) Iterator() *Iterator { | ||||
| 
 | ||||
| func (self *Trie) Copy() *Trie { | ||||
| 	cpy := make([]byte, 32) | ||||
| 	copy(cpy, self.roothash) | ||||
| 	copy(cpy, self.roothash) // NOTE: cpy isn't being used anywhere?
 | ||||
| 	trie := New(nil, nil) | ||||
| 	trie.cache = self.cache.Copy() | ||||
| 	if self.root != nil { | ||||
| @ -131,7 +131,7 @@ func (self *Trie) Update(key, value []byte) Node { | ||||
| 	self.mu.Lock() | ||||
| 	defer self.mu.Unlock() | ||||
| 
 | ||||
| 	k := CompactHexDecode(string(key)) | ||||
| 	k := CompactHexDecode(key) | ||||
| 
 | ||||
| 	if len(value) != 0 { | ||||
| 		node := NewValueNode(self, value) | ||||
| @ -149,7 +149,7 @@ func (self *Trie) Get(key []byte) []byte { | ||||
| 	self.mu.Lock() | ||||
| 	defer self.mu.Unlock() | ||||
| 
 | ||||
| 	k := CompactHexDecode(string(key)) | ||||
| 	k := CompactHexDecode(key) | ||||
| 
 | ||||
| 	n := self.get(self.root, k) | ||||
| 	if n != nil { | ||||
| @ -164,7 +164,7 @@ func (self *Trie) Delete(key []byte) Node { | ||||
| 	self.mu.Lock() | ||||
| 	defer self.mu.Unlock() | ||||
| 
 | ||||
| 	k := CompactHexDecode(string(key)) | ||||
| 	k := CompactHexDecode(key) | ||||
| 	self.root = self.delete(self.root, k) | ||||
| 
 | ||||
| 	return self.root | ||||
| @ -336,7 +336,7 @@ func (self *Trie) mknode(value *common.Value) Node { | ||||
| 	case 2: | ||||
| 		// A value node may consists of 2 bytes.
 | ||||
| 		if value.Get(0).Len() != 0 { | ||||
| 			key := CompactDecode(string(value.Get(0).Bytes())) | ||||
| 			key := CompactDecode(value.Get(0).Bytes()) | ||||
| 			if key[len(key)-1] == 16 { | ||||
| 				return NewShortNode(self, key, NewValueNode(self, value.Get(1).Bytes())) | ||||
| 			} else { | ||||
|  | ||||
		Loading…
	
		Reference in New Issue
	
	Block a user