视频游戏如何有效地存储/检索大量数据?

时间:2009-03-30 18:42:49

标签: storage

例如,在辐射3中,一个保存游戏存储游戏中每个对象和NPC的状态和位置,并且只占用几个MB。他们是怎么做到的!?!?

然后,在游戏过程中,如何在内存中添加/检索这些数据,以便它可以实时显示给玩家?

更新:(我打算让你为你的答案工作:P)

根据Kevin Crowell的回答...... 所以我猜你会有一个适用于对象和NPC的渲染距离,你会在给定范围内“选择”对象和NPC。但是,为了获取这些对象,您将使用什么类型的数据存储?

换句话说,你会在游戏中拥有一个巨大的每个对象数组,并不断更新一个包含可见对象的较小列表来渲染吗?

另外,根据Chaos的回答...... 如果你最终触及游戏中的每一个物体,会发生什么?你的拯救游戏会变得越来越大吗?在辐射3的情况下,我很确定没有“阶段”,过去的数据可能会被删除。当您离开/返回某个位置时,一切都会持续存在。那么您认为这个具体案例如何实施?

9 个答案:

答案 0 :(得分:12)

现在有了所有的大硬盘,即使开发人员似乎也忘记了兆字节中有多少字节。所以回答标题中的问题:游戏通过创建几兆字节的存档来存储大量数据。

为了说明一兆字节有多大,它是800万比特。这足以编码2 ^ 8000000 = 10 ^ 2666666个状态。相比之下,宇宙中只有10 ^ 80个原子。现在在(保存)游戏中有多个子系统具有不同的状态;例如在RPG中,每个NPC都有自己的状态。但是,有多少国家,真的吗?他们在一个城镇的位置可能会被保存为16位(你还记得他们确切的位置,如果他们还在四处走动吗?)。他们的情绪/性格/等等是另外8位,这使得一些人有更多的情绪。

在游戏中存储此类数据时,典型的数据结构是QuadTree。这是一个数据结构,允许您在O(log N)中确定某个X-Y区域中的对象。在某些情况下,游戏开发人员发现在区域中对世界进行预分区更容易。这减少了运行时计算量。毁灭战士就是一个很好的例子。它的地图具有预先计算的可见度;对于每个点,可以快速确定它属于哪个区域,并且对于每个区域,预先计算可见对象的数量。这减少了需要运行时可见性检查的对象数量。

答案 1 :(得分:8)

它可以简单地将对象或NPC映射到X,Y,Z坐标平面。那些便宜存储的信息。

在游戏过程中,所有这些对象仍然始终映射到坐标系。他们只需要读取保存信息并从那里开始。

答案 2 :(得分:8)

我认为你高估了存储/检索内容的复杂性。您不需要存储对象或其纹理的3D模型,也不需要存储构成游戏大小的磁盘大小的任何东西。

首先,正如提到的混乱一样,只需要存储有关已移动事物的信息。即使这样,你可能只需要为每一个存储新的位置和方向(假设没有涉及其他变量,比如“损坏”)。这就是每个对象的两个向量,每个对象的总共大约24个字节。这意味着您可以存储每兆字节40,000个对象的信息。这是移动的很多物品。

恢复此数据并不比首先放置对象复杂。每个对象必须具有为游戏定义的默认位置/方向以将其放置在某处,因此您所做的只是将默认值替换为保存文件中的存储值。这并不复杂,也不需要任何重要的额外处理。

答案 3 :(得分:4)

特别是在“辐射3”中,地图以网格方式划分。您只能看到当前的正方形和紧接着的正方形。数据存储的类型并不重要 - 可以是SQLite数据库,可以是序列化为磁盘的树,也可以是完全不同的。

  

...你会有一个   巨大的每一个对象的数组   游戏,不断更新更小   保存可见对象的列表   呈现?

通常是的,但“巨大的数组”不需要在内存中。还有更多列表 - 当前和相邻网格中的对象(可以从后面攻击 - 不在可见列表中),可见列表,计时器列表......

  

如果你最终触及游戏中的每个物体,会发生什么?你会救吗?   游戏变得越来越大?

可能 - 如果所有内容都有默认状态表,则保存只能包含差异。随着您的进步,保存将会增长。

  

离开/返回某个地点时,一切都会持续存在。

不。你掉到屋外的物品最终会消失。也许是机构。随机怪物每隔一段时间重生一次。这对游戏设计师来说既方便又符合现实世界。

答案 4 :(得分:3)

如果您考虑保存它所需要的信息,那真的不是那么多;

E.g。

  • 位置
  • 取向
  • 广告
  • 健康
  • 目标状态

当然还有很多,其中很多都取决于游戏类型和保存结构的组织方式。

某些类似Resident Evil的游戏只允许您在进入新区域时进行保存,这意味着您不必存储两个区域中实体的所有信息。当您“加载”保存时,它们的属性来自光盘。

至于如何检索/修改数据,我不太清楚我理解。它只是控制台内存中的数据。当玩家将其保存时,将其写入保存设备,并在加载时将其恢复。

答案 5 :(得分:2)

一种主要技术是差异保存:只保存不是默认状态的状态。比较和对比“保存游戏世界中每个对象的状态和位置”,“保存游戏世界中每个对象的状态和位置玩家已经移动或改变”。

答案 6 :(得分:1)

与其他答案相呼应,最大的节省来自消除所有不必要的状态数据。

如果你看一下8位的侧滚动游戏,他们会在屏幕外显示时立即放弃状态,并且通常不会保留任何内容,因为他们的资源太紧,不能保持超过最小实例数。< / p>

在“辐射3”这样的游戏的宏观层面上进行此操作只是增加了问题的范围。您开始通过网格或其他几何方法对景观进行切片,并在玩家从一个部分移动到下一个部分时生成/消失。理想情况下,每个区域的大小都要小,以便内存状态不高。您可以找出保留NPC和项目实例所需的最小状态,并在布局数据中尽可能标记自动重新生成,以便不需要保存任何状态。

如果要指向特定的数据结构,示例序列化格式可能是由指针树索引的线性流,其中树的组织对应于地图布局。

答案 7 :(得分:1)

在相关的说明中,游戏引擎通常使用Zip压缩,以保持所有内容的大小,并使一些操作更快。

答案 8 :(得分:1)

除了别人说的话,我想补充状态并不是必然意味着只是位置和运动,而是适合各自的状态。通常游戏引擎有一个功能,允许您保存某个类的数据。

假设您有一个Player类,并且您很好地了解了这个故事,当您单击保存可以存储的可能数据时:

  • 玩家位于哪里? 的水平/地图
  • 他的属性是什么: 健康,法力,实力, 情报等
  • 他有什么技能。
  • 他的等级。

在全球范围内我们也可以:

  • 有多少引用(允许引擎从列表中拾取对象的名称)到对象的数量存储在该特定级别,换句话说,当您加载应加载的对象时用它。
  • 我们是否正在使用物理,如果是这样,谁使用它。

还有更多。 “辐射3”有一种类型的保存,另一种游戏则有另一种类型。这实际上取决于使用的类型和引擎。