[Unity] Basic Cache Pool

Cache pool requirements
1. Have a common storage space
2. Get it from this common space when we need an object.
If there is a desired object in the space, return directly to use.
If there is no desired object in the space, create a required object and return.
3. When the object is used, it is not deleted, but put into this public space for the next use.


The role of the cache pool
Put frequently used objects into the cache pool, you can save the cup overhead, but there will be memory overhead. Typical performance of using memory for CPU performance. General bullets, special effects and other related objects will use the buffer pool.

Principles of
Insert picture description here
making ideas The
cache pool is a manager role (singleton mode). The
cache pool can be used as a variety of object containers (Dictionary + List). The
cache pool can be taken and put:
put into the method
take out the method

Cache Pool Knowledge
1. Singleton Mode
2.
Dictionary
3. List 4. GameObject.SetActive ()
5. GameObject.Instantiate
6.Resources.load

Code

/// <summary>
/// 单例模式基类
/// </summary>
/// <typeparam name="T"></typeparam>
public class BaseManger<T> where T : new()

{
    private static T _instance;

    public static T instance
    {
        get
        {
            if (_instance == null)
            {
                _instance = new T();
            }
            return _instance;
        }

    }

}

/// <summary>
/// 缓存池模块
/// 1.Dictionary List
/// 2.Gameobject和Resources 两个公共类的API
/// </summary>
public class poolMgr:BaseManger<poolMgr> 
{
    //缓存池容器
    public Dictionary<string, List<GameObject>> poolDic = new Dictionary<string, List<GameObject>>();

    /// <summary>
    /// 往外拿东西 
    /// name是预设体的名字和路径
    /// </summary>
    /// <param name="name"></param>
    /// <returns></returns>
    public GameObject GetObj(string name)
    {
        GameObject obj = null;

        //缓存池里有gameobject
        if (poolDic.ContainsKey(name) && poolDic[name].Count > 0)
        {
            obj = poolDic[name][0];
            poolDic[name].RemoveAt(0);
        }
        //缓存池没有,加载预设体
        else
        {
            obj = GameObject.Instantiate(Resources.Load<GameObject>(name));
            //把对象名字改的和池子名字一样
            obj.name = name;
        }

        //取出来的时候激活
        obj.SetActive(true);

        return obj;
    }

    /// <summary>
    /// 还暂时不用的东西
    /// </summary>
    public void PushObj(string name,GameObject obj)
    {
        //放进去的时候让gameobject失活
        obj.SetActive(false);

        //里面有gameobject
        if (poolDic.ContainsKey(name))
        {
            poolDic[name].Add(obj);
        }
        //里面没有
        else
        {
            poolDic.Add(name, new List<GameObject>() { obj });
        }
    }
}

Test
Write a test script, mount the empty object Gameobject, press the left button to create a Cube, and the right button to create a Sphere.

public class PoolTest : MonoBehaviour
{
    void Update()
    {
        if (Input.GetMouseButtonDown(0))
        {
            poolMgr.instance.GetObj("Test/Cube");
        }
        if (Input.GetMouseButtonDown(1))
        {
            poolMgr.instance.GetObj("Test/Sphere");
        }
    }
}

Create preset bodies of Cube and Sphere in the Resources / Test directory
Insert picture description here


Write a script that is delayed into the buffer pool and mount it on Cube and Sphere.

public class DelayPush : MonoBehaviour
{
    //当对象激活时 会进入的生命周期函数
    void OnEnable()
    {
        Invoke("push", 1);
    }

    // Update is called once per frame

    void push()
    {
        poolMgr.instance.PushObj(this.gameObject.name, this.gameObject);
    }
}

Insert picture description here
Disadvantages: exposed to the Hierarchy panel, it is best to be placed under a parent object level.

Posted 28 original articles · praised 3 · visits 883

Guess you like

Origin blog.csdn.net/wangpuqing1997/article/details/105572378
Recommended