Pool.cs 1.6 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051
  1. // Pool to avoid allocations (from libuv2k & Mirror)
  2. using System;
  3. using System.Buffers;
  4. using System.Collections.Generic;
  5. namespace ET
  6. {
  7. public class Pool<T>
  8. {
  9. // Mirror is single threaded, no need for concurrent collections
  10. readonly Stack<T> objects = new Stack<T>();
  11. // some types might need additional parameters in their constructor, so
  12. // we use a Func<T> generator
  13. readonly Func<T> objectGenerator;
  14. // some types might need additional cleanup for returned objects
  15. readonly Action<T> objectResetter;
  16. public Pool(Func<T> objectGenerator, Action<T> objectResetter, int initialCapacity)
  17. {
  18. this.objectGenerator = objectGenerator;
  19. this.objectResetter = objectResetter;
  20. // allocate an initial pool so we have fewer (if any)
  21. // allocations in the first few frames (or seconds).
  22. for (int i = 0; i < initialCapacity; ++i)
  23. objects.Push(objectGenerator());
  24. }
  25. // take an element from the pool, or create a new one if empty
  26. public T Take() => objects.Count > 0 ? objects.Pop() : objectGenerator();
  27. // return an element to the pool
  28. public void Return(T item)
  29. {
  30. if (this.Count > 1000)
  31. {
  32. return;
  33. }
  34. objectResetter(item);
  35. objects.Push(item);
  36. }
  37. // clear the pool
  38. public void Clear() => objects.Clear();
  39. // count to see how many objects are in the pool. useful for tests.
  40. public int Count => objects.Count;
  41. }
  42. }