0

我正在开发一款在线游戏,它将玩家的进度保存到 MySQL 数据库中,并且我正在尝试优化性能。该数据将采用与特定进度成就相对应的 ID 形式。这些“成就”将包括与 NPC 交谈、发起任务、完成任务等,因此 ID 将不按特定顺序添加到数据库中。在以下情况下,我目前无法决定如何存储成就数据:

1)作为“玩家”表上的逗号分隔文本字段(例如 32,2,53,1,3,5)。每次触发成就时,相应的 ID 都会添加到文本字段的末尾。PHP 端将使用 strpos 执行检查。

2)存储为 Player_Progress 表中的记录。这可能意味着每个玩家有大量(约 100 条)记录,我不知道这会如何影响性能。

我知道分隔字段是不受欢迎的,但是看到数据只检查了几次,并且只添加到(未删除),我想知道在这种情况下规范化是否有点矫枉过正?

4

1 回答 1

2

如果您要始终将所有内容读入游戏客户端,将状态保持在那里(可能在字典或哈希表中),然后只需将数据库用作平面持久性/序列化存储,我认为这没关系。然而,这条线抓住了我:

PHP 端将使用 strpos 执行检查。

这听起来像是您想查询个人成就,并且这里肯定会推荐使用数据库,原因有两个:

  1. 您不想在每次向服务器发出请求时读取整个字符串并反序列化它。不费力气就不会在请求之间保持状态。我读了上面的声明是说这个游戏不是在本地客户端上运行的,而是在浏览器中不断地向服务器发出请求。
  2. 您可以利用数据库的强大功能。

使用标准化数据库,您可以通过以下查询简单地检查给定玩家的成就:

SELECT 1
FROM achievements
WHERE playerId = @playerId
AND achievementId = @achievementId

并且有了正确的索引,这应该是闪电般的速度。

如果您只有一个字符串,您必须首先从数据库中检索序列化的 blob,然后将其解析为可用的数据结构,或者逐个检查每个字符以找到您要查找的数据。这似乎是更多的开销。

作为额外说明,每个玩家 100 行,即使您有 1,000,000 名玩家,也不是真正的“很多”行。

于 2014-03-08T04:29:35.880 回答