知乎热榜 ( ) • 2024-03-28 14:33
琴梨梨OvO的回答

和steam有一些关系,但没有这么简单

在很早时期,游戏的资源文件都是零碎放置的,一个游戏可以有成千上万个资源文件

因为早期游戏体积不大,资源文件数量也不算多,所以没啥问题这么做

后来随着资源越来越大越来越多,但当时主流媒介是机械硬盘和光盘,就出现了一个问题:零碎读取跟不上

旋转媒介每读取一个文件就需要进行一次寻道,甚至可能用时比读取本身更长

这导致如果游戏需要读取大量零碎文件,读取速度就跟不上

所以就出现了资源封包的概念,把零碎资源封在一个文件以内,游戏读取单个文件并自己处理内部映射逻辑

这样的封包解决了零碎读取寻道太慢的问题,还引入了压缩算法节约空间

到这一步其实发展的都没啥问题


但是,封包一定程度上增加了游戏差分更新的难度

以前资源全部零碎放置的时代,差分更新很简单,哪些文件变化了就更新哪些,简单粗暴而且高效

封包之后,显然一次性直接更新整个巨大的封包是不可能的,那就必须引入差分算法寻找每个封包的二进制差异

那么steam的差分算法是如何推动游戏体积膨胀的呢?我们来看看steam的差分算法是怎么样的

Uploading to Steam (Steamworks Documentation)

简单来说有几个特点,第一个是steam永远会为需要更新的文件同步创建新副本最后再覆盖回去,所以需要2倍待更新文件的硬盘空间,第二个是steam按1m大小划分块,所以如果整个文件长度发生了很多变化,尽管只是内容整体偏移,也可能产生很大的更新体积

所以理论上来说,针对steam的更新机制开发的时候,应该引入一些padding策略来尽可能减少大范围的文件更新

但问题就在于,很多游戏开发阶段根本没有注意steam更新的策略,就引入了一些与steam更新策略八字不合的设计,比如不定长还带时间戳的toc遍布整个封包,更新封包内1kb文件就导致整个封包都被diff算法算进去了

而且这个问题往往是在第一次推送更新的时候才被发现,也就是此时往往第一个发布版本已经被很多用户下载了,调整封包格式已经来不及了

玩家往往会抱怨要很长时间更新才能玩上,对于多人在线游戏尤其,所以很多开发商就采取了一个骚操作:直接把产生变化的文件打入一个patch封包,并修改引擎使其优先从patch封包加载资源

这种做法确实对于steam的更新机制非常友好,可以把更新体积控制在真的只有实际差异左右的大小,玩家每次更新只需要下载数m的小文件并且不用磨半天硬盘

但这种做法有什么问题呢,就是一个资源文件的旧版本和新版本实际上同时存在,多消耗了一倍空间

于是随着游戏不断更新,产生越来越多的patch封包,越来越多文件实际上双倍消耗空间了,最后的结果就是体积膨胀,比如GTA5的patch depot大小已经比发布时本体的大小还大了

steamdb.info/depot/2715

这就是很多持续运营型游戏体积越来越膨胀的原因,所以堡垒之夜才会弄过一次性推倒膨胀更新(代价是下载几十g的更新几乎是把游戏重下一遍,才能把100g压缩到30多g,而且又随着更新再次膨胀了)

对于一些单机游戏,如果已经有封包和解包工具,自己把更新包与主包合并后不会影响游戏运行并且能节约很多空间,代价则是下次更新需要全量下载


当然,也不是所有开发商都会这么做

像是unity之类的引擎本身封包就有为steam差分更新优化,开发者正常打包也不会产生过大的差分大小

又比如育碧就是一家很有个性的开发商,一个60g的更新一次更新要下载40g对于育碧来说是可接受的,所以育碧的游戏就没有那么离谱的空间膨胀

近些年也有一些开发商发现反正现在ssd普及了零碎读取不是问题了,倒车回古早一个游戏成千上万文件的时代倒也没啥问题了,开始搞零碎封包,每个封包只有数m,也变相的解决了这个问题



所以总的来说,是steam的差分更新机制与现代持续运营型游戏的经营思路共同助推了游戏的体积膨胀,而steam差分更新机制导致空间膨胀的原因又是游戏资源封包化