chore: decrease DomainTrie's memory use

This commit is contained in:
wwqgtxx
2022-11-30 18:50:46 +08:00
parent 1d9e320087
commit 84caee94af
6 changed files with 58 additions and 12 deletions

View File

@ -73,11 +73,7 @@ func (t *DomainTrie[T]) insert(parts []string, data T) {
// reverse storage domain part to save space
for i := len(parts) - 1; i >= 0; i-- {
part := parts[i]
if !node.hasChild(part) {
node.addChild(part, newNode[T]())
}
node = node.getChild(part)
node = node.getOrNewChild(part)
}
node.setData(data)
@ -123,6 +119,10 @@ func (t *DomainTrie[T]) search(node *Node[T], parts []string) *Node[T] {
return node.getChild(dotWildcard)
}
func (t *DomainTrie[T]) FinishInsert() {
t.root.finishAdd()
}
// New returns a new, empty Trie.
func New[T any]() *DomainTrie[T] {
return &DomainTrie[T]{root: newNode[T]()}

View File

@ -1,5 +1,7 @@
package trie
import "strings"
// Node is the trie's node
type Node[T any] struct {
children map[string]*Node[T]
@ -8,6 +10,9 @@ type Node[T any] struct {
}
func (n *Node[T]) getChild(s string) *Node[T] {
if n.children == nil {
return nil
}
return n.children[s]
}
@ -16,9 +21,48 @@ func (n *Node[T]) hasChild(s string) bool {
}
func (n *Node[T]) addChild(s string, child *Node[T]) {
if n.children == nil {
n.children = map[string]*Node[T]{}
}
n.children[s] = child
}
func (n *Node[T]) getOrNewChild(s string) *Node[T] {
node := n.getChild(s)
if node == nil {
node = newNode[T]()
n.addChild(s, node)
}
return node
}
func (n *Node[T]) finishAdd() {
if n.children == nil {
return
}
if len(n.children) == 0 {
n.children = nil
}
children := make(map[string]*Node[T], len(n.children)) // avoid map reallocate memory
for key := range n.children {
child := n.children[key]
if child == nil {
continue
}
switch key { // try to save string's memory
case wildcard:
key = wildcard
case dotWildcard:
key = dotWildcard
default:
key = strings.Clone(key)
}
children[key] = child
child.finishAdd()
}
n.children = children
}
func (n *Node[T]) isEmpty() bool {
if n == nil || n.inited == false {
return true
@ -37,13 +81,7 @@ func (n *Node[T]) Data() T {
func newNode[T any]() *Node[T] {
return &Node[T]{
children: map[string]*Node[T]{},
children: nil,
inited: false,
data: getZero[T](),
}
}
func getZero[T any]() T {
var result T
return result
}