github.com/zerosnake0/jzon@v0.0.9-0.20230801092939-1b135cb83f7f/node.go (about)

     1  package jzon
     2  
     3  import (
     4  	"sync"
     5  )
     6  
     7  var (
     8  	nodeStackPool = sync.Pool{
     9  		New: func() interface{} {
    10  			return &nodeStack{}
    11  		},
    12  	}
    13  )
    14  
    15  type readNode struct {
    16  	m     map[string]interface{}
    17  	s     []interface{}
    18  	field string
    19  }
    20  
    21  type nodeStack struct {
    22  	stack []readNode
    23  }
    24  
    25  func (ns *nodeStack) initArray(s []interface{}) *nodeStack {
    26  	ns.stack = append(ns.stack[:0], readNode{
    27  		s: s,
    28  	})
    29  	return ns
    30  }
    31  
    32  func (ns *nodeStack) initObject(m map[string]interface{}) *nodeStack {
    33  	ns.stack = append(ns.stack[:0], readNode{
    34  		m: m,
    35  	})
    36  	return ns
    37  }
    38  
    39  func (ns *nodeStack) pushArray(field string) *nodeStack {
    40  	ns.stack = append(ns.stack, readNode{
    41  		s:     make([]interface{}, 0),
    42  		field: field,
    43  	})
    44  	return ns
    45  }
    46  
    47  func (ns *nodeStack) pushObject(field string) *nodeStack {
    48  	ns.stack = append(ns.stack, readNode{
    49  		m:     map[string]interface{}{},
    50  		field: field,
    51  	})
    52  	return ns
    53  }
    54  
    55  func (ns *nodeStack) topObject() map[string]interface{} {
    56  	return ns.stack[len(ns.stack)-1].m
    57  }
    58  
    59  func (ns *nodeStack) topArray() []interface{} {
    60  	return ns.stack[len(ns.stack)-1].s
    61  }
    62  
    63  func (ns *nodeStack) setTopObject(key string, value interface{}) {
    64  	ns.stack[len(ns.stack)-1].m[key] = value
    65  }
    66  
    67  func (ns *nodeStack) appendTopArray(value interface{}) {
    68  	l := len(ns.stack) - 1
    69  	ns.stack[l].s = append(ns.stack[l].s, value)
    70  }
    71  
    72  func (ns *nodeStack) popObject() {
    73  	l := len(ns.stack) - 1
    74  	first := &ns.stack[l]
    75  	next := &ns.stack[l-1]
    76  	if next.m != nil {
    77  		next.m[first.field] = first.m
    78  	} else {
    79  		next.s = append(next.s, first.m)
    80  	}
    81  	ns.stack = ns.stack[:l]
    82  }
    83  
    84  func (ns *nodeStack) popArray() {
    85  	l := len(ns.stack) - 1
    86  	first := &ns.stack[l]
    87  	next := &ns.stack[l-1]
    88  	if next.m != nil {
    89  		next.m[first.field] = first.s
    90  	} else {
    91  		next.s = append(next.s, first.s)
    92  	}
    93  	ns.stack = ns.stack[:l]
    94  }
    95  
    96  func releaseNodeStack(ns *nodeStack) {
    97  	ns.stack = ns.stack[:0]
    98  	nodeStackPool.Put(ns)
    99  }