当前位置:网站首页>D41_缓冲池
D41_缓冲池
2022-08-05 05:18:00 【没那么简单GG】
为什么要用到缓冲池呢,怎么使用缓冲池呢?在以往的学习中,对于特效,子弹等总是频繁的创建与销毁,这无疑是增加了CPU的负担,为了节省计算量,我们就可以使用缓冲池。
缓冲池,可以想象为储物盒,而游戏物体可以想象为一次性筷子,当我们吃饭的时候,需要用到一次性筷子,吃完了以后随手便扔掉了,这无疑是消耗了资源的,于是我们使用家用的筷子,用过以后洗一洗,放在储物盒里面等着下次吃饭的时候再次用,而当这次买的筷子不够的时候我们才会重新买一批筷子,这无疑是节省了部分资源,却也浪费了一点储存空间,因为筷子不用的时候总是要放在储物盒里,故,缓冲池是用空间换取了时间。
代码原理便是创建一个集合(储物盒),需要实例化游戏物体之前先在集合中看一下有没有这个游戏物体(筷子),如果没有,便实例化(买)一个,如果有的话,便把这个游戏物体拿出来用——将它激活;需要删除一个游戏物体(筷子)的时候,直接使其失活即可。
下面来展示代码:
public class ObjectPool : MonoBehaviour
{
public static ObjectPool Instance;//先来一个单例
private void Awake()
{
Instance = this;
}
List<GameObject> pool = new List<GameObject>();
public GameObject InstantiatePool(string gameObjectName)
{
GameObject go = null;
if (pool.Count <= 0)//如果集合里没有这个游戏物体便创建一个
{
go = GameObject.Instantiate(Resources.Load("Prefabs/" + gameObjectName) as GameObject);
go.name = gameObjectName;//因为克隆出来的物体都带有(clone),所以需要统一一下名字
}
else
{
go = pool[0];//如果集合里有这个游戏物体,那么就不用再次创建,用这个就行
pool.RemoveAt(0);//把这个游戏物体重集合中删除
}
go.SetActive(true);
go.transform.SetParent(null);
return go;
}
public GameObject InstantiatePool(string gameObjectName,Vector3 position,Quaternion quaternion)
{//重载一下,方便其他类的调用
GameObject go = InstantiatePool(gameObjectName);
go.transform.position = position;
go.transform.rotation = quaternion;
return go;
}
public void RemovePool(GameObject gameObject)
{
pool.Add(gameObject);//把该游戏物体加进集合里
gameObject.SetActive(false);
gameObject.transform.SetParent(transform);
}
}上面代码中需要用到资源的动态加载,即Resources.Load("Perfabs/"+gameObjectName),需要这个游戏物体的时候再从Resource文件夹中寻找。
那么问题来了,我们的游戏中可不止这一种物体需要频繁的创建销毁,那么每一种我都要写一个吗,故,进阶版缓冲池他来了,类似于储物盒,我们给他细化一下,一片区域放筷子,一片区域放碟子,一片区域放叉子......这样的话,一个盒子便可以解决所有的问题,那么问题来了,这个大盒子该用什么数据类呢,既要能保存集合,又要方便查找。于是于是,我们自然而然就想到了字典。
下面继续展示代码:
(大致相同,只是多加了一层字典,所以就不详细注释了)
public class GameObjectPool : MonoBehaviour
{
public static GameObjectPool Instance;
private void Awake()
{
Instance = this;
}
Dictionary<string, List<GameObject>> pool = new Dictionary<string, List<GameObject>>();
public GameObject InstantiatePool(string gameObjectName)
{
GameObject go = null;
if (pool.ContainsKey(gameObjectName))
{
if (pool[gameObjectName].Count > 0)
{
go = pool[gameObjectName][0];
pool[gameObjectName].RemoveAt(0);
}
}
if (go == null)
{
go = GameObject.Instantiate(Resources.Load("Pool/" + gameObjectName) as GameObject);
go.name = gameObjectName;
}
go.SetActive(true);
go.transform.SetParent(null);
return go;
}
public GameObject InstantiatePool(string gameObjectName, Vector3 position, Quaternion quaternion)
{
GameObject go = InstantiatePool(gameObjectName);
go.transform.position = position;
go.transform.rotation = quaternion;
return go;
}
public void DestoryPool(GameObject go)
{
if (pool.ContainsKey(go.name))
{
pool[go.name].Add(go);
}
else
{
pool.Add(go.name, new List<GameObject>());
pool[go.name].Add(go);
}
go.SetActive(false);
go.transform.SetParent(transform);
}
}边栏推荐
猜你喜欢

沁恒MCU从EVT中提取文件建立MounRiver独立工程

电子产品量产工具(1)- 显示系统实现

LeetCode刷题之第746题

每日一题-电话号码的字母组合-0717

OSPF网络类型

【UiPath2022+C#】UiPath数据类型

九、响应处理——内容协商底层原理

2020年手机上最好的25种免费游戏
![[Pytorch study notes] 10. How to quickly create your own Dataset dataset object (inherit the Dataset class and override the corresponding method)](/img/71/f82e76085f9d8e6610f6f817e2148f.png)
[Pytorch study notes] 10. How to quickly create your own Dataset dataset object (inherit the Dataset class and override the corresponding method)

MySQL主从复制—有手就能学会的MySQL集群搭建教程
随机推荐
《基于机器视觉的输电线路交叉点在线测量方法及技术方案》论文笔记
深度学习系列(一)简介、线性回归与成本函数
如何使用Houdini进行程序化优化?
多边形等分
【Promise高级用法】实现并行和串行API
六步搞定子网划分
网络信息安全运营方法论 (上)
ACL 的一点心得
成功的独立开发者应对失败&冒名顶替综
LeetCode刷题之第33题
每日一题-合并K个升序链表-0722
LeetCode刷题之第61题
UE4美术你有必要了解的数学基础
idea 快速日志
CAN、CAN FD
读论文- pix2pix
LeetCode刷题之第74题
Jupyter notebook选择不同的Anaconda环境作为内核运行
【Shell编程】第一章:子串
对象比较