node_pool.go 1.9 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475
  1. // Copyright 2021 Andrew Werner.
  2. //
  3. // Licensed under the Apache License, Version 2.0 (the "License");
  4. // you may not use this file except in compliance with the License.
  5. // You may obtain a copy of the License at
  6. //
  7. // http://www.apache.org/licenses/LICENSE-2.0
  8. //
  9. // Unless required by applicable law or agreed to in writing, software
  10. // distributed under the License is distributed on an "AS IS" BASIS,
  11. // WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or
  12. // implied. See the License for the specific language governing
  13. // permissions and limitations under the License.
  14. package abstract
  15. import "sync"
  16. type nodePool[K, V, A any] struct {
  17. interiorNodePool, leafNodePool sync.Pool
  18. }
  19. var syncPoolMap sync.Map
  20. func getNodePool[K, V, A any]() *nodePool[K, V, A] {
  21. var nilNode *Node[K, V, A]
  22. v, ok := syncPoolMap.Load(nilNode)
  23. if !ok {
  24. v, _ = syncPoolMap.LoadOrStore(nilNode, newNodePool[K, V, A]())
  25. }
  26. return v.(*nodePool[K, V, A])
  27. }
  28. func newNodePool[K, V, A any]() *nodePool[K, V, A] {
  29. np := nodePool[K, V, A]{}
  30. np.leafNodePool = sync.Pool{
  31. New: func() interface{} {
  32. return new(Node[K, V, A])
  33. },
  34. }
  35. np.interiorNodePool = sync.Pool{
  36. New: func() interface{} {
  37. n := new(interiorNode[K, V, A])
  38. n.Node.children = &n.children
  39. return &n.Node
  40. },
  41. }
  42. return &np
  43. }
  44. func (np *nodePool[K, V, A]) getInteriorNode() *Node[K, V, A] {
  45. n := np.interiorNodePool.Get().(*Node[K, V, A])
  46. n.ref = 1
  47. return n
  48. }
  49. func (np *nodePool[K, V, A]) getLeafNode() *Node[K, V, A] {
  50. n := np.leafNodePool.Get().(*Node[K, V, A])
  51. n.ref = 1
  52. return n
  53. }
  54. func (np *nodePool[K, V, A]) putInteriorNode(n *Node[K, V, A]) {
  55. children := n.children
  56. *children = [MaxEntries + 1]*Node[K, V, A]{}
  57. *n = Node[K, V, A]{}
  58. n.children = children
  59. np.interiorNodePool.Put(n)
  60. }
  61. func (np *nodePool[K, V, A]) putLeafNode(n *Node[K, V, A]) {
  62. *n = Node[K, V, A]{}
  63. np.leafNodePool.Put(n)
  64. }