情况:
unity开发过程中,避免GC是很重要的一个问题。开发过程中会new比较多的局部变量,放任不管的话就会产生挺多GC。那怎么办呢?下面提供一种思路。
思路:
把创建的变量缓存起来,最多缓存40个,缓存的数据能重复利用。这样能很大程度的避免GC,当然这样内存会耗费一点,不过大多数情况下这东西还是有点用的。
使用:
var res = PoolObject<List<int>>.Alloc();
res.Add(1);
PoolObject<List<int>>.Free(res);
代码:
public static class PoolManager
{
private static Dictionary<string, IPoolObject> m_Dict;
public static void Register(string name, IPoolObject iPoolObject)
{
if (m_Dict == null) m_Dict = new Dictionary<string, IPoolObject>();
m_Dict[name] = iPoolObject;
}
public static void Clear()
{
if (m_Dict == null) return;
foreach (var element in m_Dict)
{
element.Value.Clear();
}
m_Dict = null;
}
}
public interface IPoolObject
{
void Clear();
}
public class PoolObject<T> : IPoolObject where T : class, new()
{
private static bool m_Register = false;
private static int maxCount = 40;
private static List<T> m_pooledObject = new List<T>(10);
public static T Alloc()
{
if (!m_Register)
{
m_Register = true;
PoolManager.Register(typeof(T).ToString(), new PoolObject<T>());
}
if (m_pooledObject.Count > 0)
{
var res = m_pooledObject[m_pooledObject.Count - 1];
m_pooledObject.RemoveAt(m_pooledObject.Count - 1);
return res;
}
return new T();
}
public static void Free(T poolObject)
{
if (m_pooledObject.Contains(poolObject)) return;
if (m_pooledObject.Count < maxCount)
{
m_pooledObject.Add(poolObject);
if (poolObject is IList list)
{
list.Clear();
}
else if (poolObject is IDictionary dict)
{
dict.Clear();
}
}
}
public void Clear()
{
m_Register = false;
m_pooledObject.Clear();
}
}