约束性能和容量规模的因素归纳起来是:数据共享域,消息广播域,运算共享域。这几个因素涉及的对象数量会直接影响了架构涉及,下面分别来说。
分类特征:
玩家数据总量,同时在线数
这里是指,玩家登录后,需要从多大规模的数据中读取自己的数据。social game全局共享的角色数据(统一世界),随着玩家数量增多线性增长,往往单机储存不能满足需求,需要分布式储存技术。而对于传统MMORPG,由于是分服(服务器之间是平衡世界,角色数据相互独立),相当于天然地用服务器id做了数据分区(而不需要像分布式储存那样考虑分区算法的扩展性问题),除了登录信息,没有全局数据,单机储存即可解决问题。
AOI范围与频率
这里指的是游戏过程中,即时广播涉及的对象数量以及消息密度,比如同屏玩家数。竞技和休闲类游戏通常比较小,而传统MMORPG通常较大。
范围和频率还影响client间传输消息的方式,通常有两种:client间直传(P2P); 中心服转发。从延时来看,广域网游戏这两者区别到不大(前提是中心服不卡,其实可以看做一个路由器)。如果广播范围 x 频率较大,中心服的带宽成本很高(嗯嗯,带宽是很贵的)。如果采用纯P2P,则需要考虑客户端作弊问题。当然还可以用混合的方法,即中心服监督下的P2P,比如有些竞技游戏在服务端也做一层校验,查出外挂的可能,当然这个不容易实现得好。 大部分情况下,服务器监督一切,最省心。
AOI跳转方式
是指在不同运算共享域和广播域直接切换的方式,分为无缝和跳转点。举个例子,休闲游戏和竞技游戏通常是玩家主动点击进入或退出房间/频道,不同房间/频道分隔了广播域。而即时制MMORPG(比如WOW)区域之间是无边界的。这两者区别影响运算性能的扩展性,即实现多进程处理的技术难度。对于前者可以很容易实现多进程分担处理任务。后者的无缝AOI,要实现多进程的话,在边界处需要较复杂的进程数据同步技术。
实时性/同步要求
网络延时的前提下,同步方案主要是用户体验和数据正确性之间的权衡。竞技和动作游戏强调打击感和位置准确性,需要很高的同步要求。很多游戏采用帧同步方案,即一旦对应帧数据未到,卡住整个客户端(dota的等待连线)。也有采用运动补偿的方式(也称追影),即客户端预判,当和服务端位置不一致时,通过加速等方式平滑追上。为了减少延时带来的影响,一部分计算放在客户端,关键计算等待服务器返回。在等待服务器返回结果的过程中,通常结合美术和技术手段"欺骗"玩家的视觉(比如起手动作),达到较好的体验。
Social game
玩法:策略经营类,好友互动
玩家数量大,冷数据总量大 (海量玩家同一交互域),同时在线高;
AOI范围中。频率低。消息在好友之间分发(好友数量一般在一百以内)
实时性/同步要求:低,不需要实时。运算较简单(看成是海量数据的CURD应用)
技术特点:跟微博,QQ群等传统互联网应用比较接近:数据量大,AOI范围中,实时要求低。主要难点在于读写规模大,总数据量大,cache热度不明显(无明显热数据)。
性能扩展:依赖于分布式储存和读写技术,与一般社交网络技术类似。由于需要预先加好友,设定好友数量上限可以限制数据广播的规模。
休闲棋牌类游戏
玩家数量大;冷数据总量大;但登录后通常进入房间。
房间之间分隔了广播域,游戏局之间玩家互相独立(除了聊天频道)。意味着较容易根据房间和游戏分服/进程,性能扩展容易。
AOI范围低(一局游戏的几个人),实时性一般。运算一般(棋牌算法计算)。
架构上通常分前端(登录和房间逻辑)和后端(具体一局游戏),分服设计较容易。通常一个前端要对应很多种不同类型的后端逻辑(各种类型游戏),需要制定一个容易开发和接入的框架。
容量扩展:由于游戏局的独立性,分进程/分服做运算扩展比较简单。 通过分区分房间限制了数据广播规模。
竞技类游戏
玩法:dota, FPS, 格斗动作类
AOI范围低(10人以下),交互频率高
实时交互和同步要求极高(技术难点)
容量扩展:通常与休闲类一样,先进入房间(有些叫频道)限制数据广播规模。不同房间互相独立,因此也较容易通过增加进程/服务器分散运算规模。
即时制MMORPG
通常技能有cooldown, 玩家之间可以穿插(没有动态碰撞检测),同步要求低于动作类和dota网游。单服同时在线人数有限(1w人左右),逻辑复杂, IO通常单机就可搞定。AOI通常是运算瓶颈,要提高容量就要分进程或分线程。对于区域间无缝世界,在边界处的对象,由于互相可见且可战斗,分管两个区域的进程间需要较复杂的同步机制。比如bigworld用的是对象代理技术,即在原区域是real对象,对端区域建立一个ghost(代理对象), 对real对象的所有状态改变即时同步到对端进程,反之对ghost操作也同步到real。也就是说玩家A在两个进程都有自己的副本,且都可写,需要借鉴分布式技术中,多Writer的数据一致性设计。
对MMORPG来说,单服人数越高,游戏的社区性和人气感就越强, 但人数越多,就越容易卡住服务器。现在都是多核的世界,基本上都是多线程/进程的架构了,多writer/reader, 数据同步,锁这些是常见技术考量点。一般功能模块交互性不强,分进程/线程难度不大,但AOI这块分进程要比较折腾。
题外话
这两年公司的校园招聘,程序员的title是虚拟世界架构师(汗 -_-!)。真正的虚拟世界应该是:数据规模大,AOI范围大,实时交互。以上还没有一种游戏同时符合几个特征,都不同程度通过分区/分服/分房间/分场景/分频道分隔了单个进程的处理规模,单台服务器的数据规模和带宽规模。当然,即使技术上可行,玩家脑子同时能处理的对象数比电脑要差多了(呃,试想数万人同处一个场景,然后走来走去,这个有游戏性可言?),这时候瓶颈不在服务器,超密集的角色,客户端的渲染效率变成瓶颈。