目录
一、资源冗余
资源冗余往往是很多项目中最为常见的内存问题之一。而其中往往AssetBundle打包策略和资源加载缓存策略又是导致冗余的最主要的两种原因。
1.主动打包和被动打包
打AB包时,依赖的资源属于被动打包。如下图中:caoyemao1_2d这个资源属于主动打包,其他的三个都属于被动打包。
2.依赖资源处理
打AB包时如果不采用依赖打包,会产生资源冗余的问题。如下图: caoyemao1_2d和caoyemao1_3d分别是spine动画caoyemao1的2D和3D预制体。
(1)分别制作AB包,会造成冗余
caoyemao1_2d的AssetBundle名称为2d,caoyemao1_3d的AssetBundle名称为3d,打AB包时利用AssetBundle Browser工具,可以看到2d和3d的AB包有冗余:
(2)资源冗余解决办法:
(2.1)先主动打依赖资源AB包
将2d和3d预制体共同依赖的资源单独打成一个共享的AssetBundle包res,这样2d和3d的AssetBundle可以分别引用这个共享资源包res。经过测试,三个AB包共341KB:
(2.2)将两个预制体打成一个AB包
经过测试得出AB包大小为317KB:
由上述数据可得出:多个小文件的压缩效率通常不如一个大文件高效。单个大的AssetBundle文件可能更容易被压缩得更小,而多个小文件则可能无法达到相同的压缩效果。所以可以根据项目需求选择适当的打包策略。如果初始加载时间和更新成本不是主要问题,可以考虑将更多资源合并到一个大的AssetBundle中。
二、代码生成的资源
运行时通过代码接口生成某些暂时性资源是非常常见的做法,但使用不当也很容易产生性能问题。
上面的代码,每次修改颜色时会实例化不同颜色的材质球,所以要记得销毁材质球。
三、加载和缓存策略
除了上文提到造成冗余的风险以外,还有其他如资源的缓存和常驻等,往往也是需要关注和完善的策略。
以加载AB包为例:加载AB包并利用Prefab实例化obj后,如果unload(false),那么只会删除AB包,并中断AB包和已经加载的资源的链接关系,Prefab仍存在内存中,下次加载AB包时就会成为冗余资源。
使用AB.unload(true)卸载时,会将AB包及Prefab、纹理网格及所实例化的对象等全部卸载。
在Unity中使用AssetBundle.Unload(bool unloadAllLoadedObjects)方法时,选择unloadAllLoadedObjects参数为true或false会有不同的效果:
- unloadAllLoadedObjects = false: 仅卸载AssetBundle本身,但不会卸载已经实例化的对象。这可能会导致冗余,因为虽然AssetBundle被卸载了,但内存中仍然保留了从该AssetBundle加载的资源和实例化的对象。
- unloadAllLoadedObjects = true: 卸载AssetBundle以及所有从该AssetBundle加载的资源和实例化的对象。这可以避免冗余,但会销毁所有相关的对象。