diff options
Diffstat (limited to 'Other/AstarPathfindingDemo/Packages/com.arongranberg.astar/Core/Pooling/ObjectPool.cs')
-rw-r--r-- | Other/AstarPathfindingDemo/Packages/com.arongranberg.astar/Core/Pooling/ObjectPool.cs | 131 |
1 files changed, 131 insertions, 0 deletions
diff --git a/Other/AstarPathfindingDemo/Packages/com.arongranberg.astar/Core/Pooling/ObjectPool.cs b/Other/AstarPathfindingDemo/Packages/com.arongranberg.astar/Core/Pooling/ObjectPool.cs new file mode 100644 index 0000000..262830c --- /dev/null +++ b/Other/AstarPathfindingDemo/Packages/com.arongranberg.astar/Core/Pooling/ObjectPool.cs @@ -0,0 +1,131 @@ +#if !UNITY_EDITOR +// Extra optimizations when not running in the editor, but less error checking +#define ASTAR_OPTIMIZE_POOLING +#endif + +using System; +using System.Collections.Generic; + +namespace Pathfinding.Util { + public interface IAstarPooledObject { + void OnEnterPool(); + } + + /// <summary> + /// Lightweight object Pool for IAstarPooledObject. + /// Handy class for pooling objects of type T which implements the IAstarPooledObject interface. + /// + /// Usage: + /// - Claim a new object using <code> SomeClass foo = ObjectPool<SomeClass>.Claim (); </code> + /// - Use it and do stuff with it + /// - Release it with <code> ObjectPool<SomeClass>.Release (foo); </code> + /// + /// After you have released a object, you should never use it again. + /// + /// Since: Version 3.2 + /// Version: Since 3.7.6 this class is thread safe + /// See: Pathfinding.Util.ListPool + /// See: ObjectPoolSimple + /// </summary> + public static class ObjectPool<T> where T : class, IAstarPooledObject, new(){ + public static T Claim () { + return ObjectPoolSimple<T>.Claim(); + } + + public static void Release (ref T obj) { + obj.OnEnterPool(); + ObjectPoolSimple<T>.Release(ref obj); + } + } + + /// <summary> + /// Lightweight object Pool. + /// Handy class for pooling objects of type T. + /// + /// Usage: + /// - Claim a new object using <code> SomeClass foo = ObjectPool<SomeClass>.Claim (); </code> + /// - Use it and do stuff with it + /// - Release it with <code> ObjectPool<SomeClass>.Release (foo); </code> + /// + /// After you have released a object, you should never use it again. + /// + /// Since: Version 3.2 + /// Version: Since 3.7.6 this class is thread safe + /// See: Pathfinding.Util.ListPool + /// See: ObjectPool + /// </summary> + public static class ObjectPoolSimple<T> where T : class, new(){ + /// <summary>Internal pool</summary> + static List<T> pool = new List<T>(); + +#if !ASTAR_NO_POOLING + static readonly HashSet<T> inPool = new HashSet<T>(); +#endif + + /// <summary> + /// Claim a object. + /// Returns a pooled object if any are in the pool. + /// Otherwise it creates a new one. + /// After usage, this object should be released using the Release function (though not strictly necessary). + /// </summary> + public static T Claim () { +#if ASTAR_NO_POOLING + return new T(); +#else + lock (pool) { + if (pool.Count > 0) { + T ls = pool[pool.Count-1]; + pool.RemoveAt(pool.Count-1); + inPool.Remove(ls); + return ls; + } else { + return new T(); + } + } +#endif + } + + /// <summary> + /// Releases an object. + /// After the object has been released it should not be used anymore. + /// The variable will be set to null to prevent silly mistakes. + /// + /// Throws: System.InvalidOperationException + /// Releasing an object when it has already been released will cause an exception to be thrown. + /// However enabling ASTAR_OPTIMIZE_POOLING will prevent this check. + /// + /// See: Claim + /// </summary> + public static void Release (ref T obj) { +#if !ASTAR_NO_POOLING + lock (pool) { +#if !ASTAR_OPTIMIZE_POOLING + if (!inPool.Add(obj)) { + throw new InvalidOperationException("You are trying to pool an object twice. Please make sure that you only pool it once."); + } +#endif + pool.Add(obj); + } +#endif + obj = null; + } + + /// <summary> + /// Clears the pool for objects of this type. + /// This is an O(n) operation, where n is the number of pooled objects. + /// </summary> + public static void Clear () { + lock (pool) { +#if !ASTAR_OPTIMIZE_POOLING && !ASTAR_NO_POOLING + inPool.Clear(); +#endif + pool.Clear(); + } + } + + /// <summary>Number of objects of this type in the pool</summary> + public static int GetSize () { + return pool.Count; + } + } +} |