本文摘要:
文/水风 本文首发知乎https://zhuanlan.zhihu.com/p/341855913现在在一款百玩DAU的游戏项目中事情,由于怕玩家找上来聊一些非技术的事情,就不报名字了,只讨论技术问题。我们游戏是一款基于skynet的通服游戏,开房间的游戏架构,预计单服可承载60w同时在线。 游戏现在已经上线两年了,上线后我们做了不少服务端优化的事情。
文/水风 本文首发知乎https://zhuanlan.zhihu.com/p/341855913现在在一款百玩DAU的游戏项目中事情,由于怕玩家找上来聊一些非技术的事情,就不报名字了,只讨论技术问题。我们游戏是一款基于skynet的通服游戏,开房间的游戏架构,预计单服可承载60w同时在线。
游戏现在已经上线两年了,上线后我们做了不少服务端优化的事情。这篇文章主要先容游戏服务端优化的一些方法,主要以先容思想为主,为了举例更容易明白,许多实现思路并不是我们游戏的,这里也是作为例子说明。1 所有的代码都要能热更所有的法式员都写过bug,bug是难免的,可是我们可以只管降低bug对玩家的影响。
而今世码上线后,若发现bug,为了不影响玩家体验,不能通过重启只能通过热更去修复。我们在skynet的基础上,做了多种热更方案,基本上能保证所有的代码都能被热更。而且,可热更,是我们新开发功效时的一个必须思量的事情。我们基于skynet、lua和服务端架构,做了以下热更方案:sharedata.update,热更筹谋设置表。
(skynet支持)lua模块的热更:我们在玩家逻辑中,将状态统一放在一个数据模块中,将逻辑放在其他模块。这样,逻辑模块就可以被随时替换。
在skynet中通过cache.clear()清理缓存代码,然后将所有的玩家服务的指定逻辑模块替换即可。service转动更新:若一个service是不停销毁而且不停建立新的,就可以使用这种方案。好比一场战斗的房间,或者玩家service在玩家登陆时建立玩家登出后销毁(我们其实是有内存池的,可是可以通过清空内存池而且接纳现有的服务)。
在skynet中通过cache.clear()清理缓存代码即可,新的service会自动使用新的代码。这个更新方案有个坏处,就是无法实时的连忙更新已建立的service,而新的service会连忙生效。
历程级此外重启或转动更新:若历程重启不会影响到整体游戏集群,那么可以通过重启历程来更新代码。好比我们的登陆服务器,可以先通过负载平衡器将流量从某一个登陆服转给其他的,然后等没有流量后重启,然后依次重启其他的。
玩家逻辑历程也是如此,可以先不在分配新玩家登陆某玩家历程,然后将当前历程玩家迁移到其他历程,然后重启之,依次执行转动更新即可。inject:skynet也支持了替换某函数,所以可以通过写一个新的函数替换老的函数。
此方案理论上可以热更所有代码,但inject代码写起来贫苦一些,尤其是很长的函数。通过以上热更方案,基本能笼罩全部情况。一般只有我们发现只能通过inject但想修改的函数很是长或者修改很是庞大以为不稳妥的时候,我们才会去通过重启修复线上问题(此情况在我们游戏中少少)。
2 只管详尽的日志完善的日志很是重要,为处置惩罚线上问题定位线上bug提供基础,也为运营盘问题提供支持。此外,也可以将日志用于下文要说的监控和报警。日志这工具,不用时没感受,用的时候就忏悔:为啥不在这里加一条日志,为啥不把这个信息打印出来。
如何记载日志,没有一个统一的尺度,我这里说一下我的履历和思考,这里主要先容非战斗逻辑的日志。哪些地方写日志:玩家一个行为对玩家状态发生改变,这个逻辑期间至少一条日志。
玩家某些行为投放物品,一般投放前。一些重要的状态切换,好比一个战斗房间由准备进入开战状态。任何错误和异常,都需要加一条错误日志,防御性编程检测到错误也需要。
日志信息,日志需要记载什么:日志的基本业务形貌,一般几个关键字。好比投放武器逻辑涉及的上下文关键信息。
好比投放武器的 武器信息,好比武器所属的玩家ID其他信息,好比服务端历程信息、时间戳、日志所属entity等。日志品级常见的又debug、info、error、fatal。一般表现的寄义是:debug:开发情况打印,线上情况不打印。一般用于法式开发。
(这里有个坑,debug日志一般的实现是线上举行过滤,但这个函数的参数还是会执行,所以如果是超级长的字符串操作要注意性能问题)info:线上情况打印,我们说的日志大部门都是这个级别。error:和log类似,只是是错误信息。一般是业务预期内的错误,不会影响系统正常运行。
fatal:业务预期外的错误,表现这类错误信息需要开发人员去关注和排查。对于战斗,最好的方案是回放录像,日志一般是次选项。
3 监控和报警通过监控,我们要对线上服务器的情况只管的相识,而且能提前发现问题,防止问题扩大化后才知道。报警和监控相辅相成,监控到异常后,马上报警,我们就能连忙对线上问题举行处置惩罚。我们用到的监控/报警有:慢响应:监控客户端请求的平均响应速度,一般能整体评估游戏服务器是否有卡顿。
FATAL日志:有些特殊情况需要马上通知开发人员,好比服务器开服失败等,服务端会打印FATAL日志。这时候就需要报警通知。线上traceback:一般用剧本写的服务端逻辑,都市有一些线上traceback,这个是需要重点关注的问题。
发现有trace就需要去确认traceback的影响,若影响玩家功效需要热更修复。投放监控:我们游戏对物品投放也有监控,防止玩家因为某些bug可以刷某类物品。由筹谋对每类物品设置一个报警上限,玩家当日获取此类物品凌驾阈值会通知到我们。我们会去检查玩家行为看是否切合预期。
玩家行为监控:除了物品获取,也有些玩家行为需要监控。好比我们游戏中天天打悬赏令的次数,根据筹谋的设计天天不会太多。
凌驾某个数量说明可能有问题,需要人工审查。服务端性能监控:我们会监控单点服务cpu使用率,skynet中一个服务只使用一个线程,单点服务cpu占用上限是一个核,所以比力容易泛起问题。我们若发现单点服务的cpu使用率凌驾阈值,就会报警,可以提前举行性能优化。
服务端机械监控:监控机械、数据库的硬件信息,好比cpu、内存等。凌驾阈值举行报警。阿里云用度监控:对按量付费的项目,我们会对其举行监控,若某一天的消费凌驾某一阈值,则举行报警。
总之,通过监控以及与之对应的报警,能提前发现线上问题,降低影响。大事化小,小事化无。
4 容错:保底逻辑大型漫衍式集群必须要思量容错问题,容错分为几个层面:架构容错(机械宕机、历程crash):主要通过消除单点等方式,后文会先容。DB等Saas服务卡顿/闪断:做好断线重连、重试等容错逻辑。
逻辑容错:有些逻辑系统中难免泛起异常、bug或者超出预期的情况,在服务端中,对于这些问题只管写一些保底逻辑,当泛起问题时,能降低问题造成的影响。下面主要先容一下逻辑容错的相关情况:系统异常:某些非焦点服务泛起异常(卡死、crash、网络中断)可以之关闭异常服务,保证系统整体正常运行。bug:好比某款游戏中的反外挂逻辑特别庞大,有时候会因为改动了某些战斗机制造成外挂的误判,把正常玩家判为外挂玩家,这种bug比力难完全制止而且会造成大规模玩家封号等较大的影响。
因此,可以增加了一个保底逻辑,每小时因外挂封号的玩家数量凌驾一个阈值以后,就不再直接封号,而是报警而且把这些玩家记载下来,去人工检查后确认是否有问题,有问题再人工操作封号。这个保底逻辑一方面可以报警让我们快速发现外挂检测bug,另一方面纵然泛起了bug也能降低影响人数。玩家行为超出预期:好比,有些游戏会记载玩家的历史挚友(删掉的),这个记载会随着玩家行为变得越来越长。
若完全没有限制,当客户端请求或者逻辑遍历历史挚友列表时,会造成卡顿。因此,这种情况最好设一个上限,历史挚友数量凌驾一个阈值就删掉之前的。功效开关:开发新功效一定要做好开关,可以随时线上关闭功效。
若出了问题,可以关闭功效后逐步修复,不影响玩家玩其他功效。5 异步提交玩家有些操作不需要等候等候逻辑执行完成返回响应,这种操作可以将任务提交到行列中然后异步执行。这种方案的利益是纵然任务处置惩罚能力不足,不会影响到玩家造成玩家卡顿。
我们曾经开发过一个副本结果排行榜,排行榜的上榜规则比力庞大,当玩家打完副本后会将战斗结果提交到排行榜,排行榜通过一系列的逻辑将结果插入到排行榜中。当我们开服后,玩家大量涌入这个新玩法,此外,由于排行榜是空的,大量结果都市进入排行榜中,造成排行榜卡顿,导致玩家完成战斗后提交结果时卡死。厥后,我们将其改为玩家打完副本后将结果提交到排行榜中,但不等候排行榜的响应。
这样,当排行榜逻辑卡顿的时候,只是有可能结果上榜会延迟,但不影响玩家体验。以skynet为例,只管用skynet.send替代skynet.call。若发现skynet.call没有返回值时,就去判断一下call的逻辑和下文逻辑是否有顺序依赖关系,若没有依赖关系就可以改为send。这其实就是消息行列的思想,通过异步处置惩罚提高系统性能和削峰、降低系统耦合性,大家可以去百度“消息行列”详细相识。
6 消除单点和水平扩展一个游戏服务器集群的承载上限,就是集群中的逻辑单点的承载上限。所以,在游戏服务器架构设计中,要只管的消除单点,改为支持水平扩展。
服务器集群中存在单点的常见原因是因为数据需要统一治理,好比玩家治理器、家族治理器等,需要治理所有玩家或者所有家族。这种情况有两种解决方案:加一层分发逻辑:好比我们之前家族治理器治理所有家族的信息以及相关的逻辑,厥后就扛不住了。然后我们抽象出来了familymaster和familynode,每个familynode治理部门家族,familynode可以无限的水平扩展。
familymaster依然是单点,可是他只是记载每个家族在哪个familynode上面,所以承载上限很高。使用无状态:将数据和逻辑分散,数据放在redis/db中,逻辑执行都去读写db。
这种方案理论上是可以无限扩展的,因为db是支持无限扩展的,可是要求状态(数据)相对比力简朴,容易存在db中而且可以高效读写。好比上文提到的familymaster依然是单点,但只治理familyid到familynode的信息,这个信息我们就可以存在redis中,然后每次读写都去操作redis,这样就到达了理论上的无限扩展。一般来说,游戏服务器并不要求完全的消除单点,因为需要做许多分外的事情,要么增加开发成本,要么增加运维成本。
所以,只要我们的单点承载上限超出游戏玩家量的需求,就可以了。不要过分优化。消除单点一方面可以带来承载量的提升(高并发),另一方面可以提高可用性(高可用)。
通过消除单点,一个功效可能漫衍在多个历程/机械上,纵然某个历程挂了,其他历程也可以使用,仍然可以提供服务。固然,写代码时需要处置惩罚这种异常才可以获得高可用性。
我们游戏的服务端简化版架构如下图所示,我们的玩家逻辑、战斗逻辑和家族逻辑都是可以水平扩展的。而只有一些治理全服信息的逻辑(好比维护玩家再哪个历程上)才会放在治理器里,治理器是服务器的单点,也是服务器承载量的瓶颈。
服务器架构(简化版)7 功效解耦和隔离凭据KISS(Keep It Stupid Simple)原则,应该将功效只管的拆分成小的代码模块。这个原则对应到游戏服务器就是要将功效只管的拆分成一个个服务,每个服务都只卖力一小块功效。Skynet提供了比力好的模块解耦模式:service模式,skynet中每个service就可以对应一个物理意义上的服务,而每个service就是一个线程,同历程service之间具有一定的隔离。
而差别service可以放在一个历程,也可以放在差别的历程,提供了差别的隔离级别。KISS原则我是基本赞成的,可是我认为游戏的玩家小我私家逻辑应该放在一个服务中,若拆为多个服务会造成服务间耦合严重。好比玩家升级,往往涉及到背包、属性、代币等差别模块。
这个地方更合适用代码模块来区离开,但运行时属于一个服务。除了玩家小我私家逻辑,其他功效可以适当的拆分,好比挚友服务、谈天服务、排行榜服务等。将功效拆为一个个服务以后,就需要思量如何隔离。

隔离方式skynet支持线程隔离和历程隔离,有的单线程服务器可能只支持历程隔离。线程隔离的优点在于差别服务运行在同一历程,挪用是函数挪用,不存在失败的观点,缺点是一定水平上违反了KISS原则,而且服务之距离离度低某些情况仍会相互影响历程隔离优点在于历程功效更单一明确,隔离度高不会相互影响,但服务间通信变为网络通信更庞大,此外,每个服务一个历程,会造成历程数量庞大,治理和维护成本高。以前我曾基于python写过游戏微服务,因为python只支持单线程,所以每个历程只能承载一个服务。
这种模式主要存在两个问题,一、服务间的挪用请求都是网络rpc,都存在失败的可能,给业务开发造成了很大的成本。二、历程数量许多,因为一类服务往往又多个实例,每个实例都是一个历程,历程数量为N*M,历程数量多造成治理难题。skynet这种模式就比力好,一个历程可以承载许多服务实例,每个服务实例一个线程,服务之间基于线程举行隔离。
差别的服务可以放在一个历程中,一个历程也可以承载多个相同或者差别类型的服务实例。那么,在skynet模式中,什么情况使用线程隔离,什么情况使用历程隔离呢?首先凭据物理寄义,将服务举行分组,同组服务放在同一历程。好比玩家服务、家族服务、登陆服务等。
这个主要是将差别的焦点服务举行隔离,也思量容易治理。对于性能消耗高的服务,举行隔离。防止打满CPU影响其他服务。对于不稳定的服务,举行隔离。
好比某服务使用了没有被广泛验证的C扩展,crash概率就会高许多。8 引入超时通过上文先容的服务拆分和隔离,我们将服务端举行了拆分,拆分后我们希望对某些服务中的异常举行进一步的隔离。skynet把集群看作一个整体,所以通过skynet.call挪用其他历程函数并等候返回默认是无限等候的,没有timeout。这样就导致若某个模块卡顿或者泛起了异常,就会导致集群雪崩,影响到所有的功效。
好比我们游戏的chat模块,曾因为某些问题导致历程卡顿,而玩家登录都市去注册和拉取谈天消息,进而导致玩家无法登录,也无法正常游戏。我们的谈天功效在前期设计的时侯设计的比力庞大,所以实现方案比力庞大,我看了一遍代码后以为重构的成本和风险都太高。
于是,我们希望纵然chat卡顿或异常,也不要影响玩家的正常游戏,只是让玩家不能谈天而已。因此,我们在skynet中增加了timeout机制,支持skynet.call超时。引入了超时后,也需要增加超时后的逻辑处置惩罚。
超时可能有三种情况,1.吸收方没有收到请求。2.吸收方收到了可是出trace没有返回响应。3.请求方没有收到吸收方发出的响应。业务需要处置惩罚超时问题,一般有两种方案:重试或忽略。
对于有些关键逻辑,需要写重试逻辑,重试要保证幂等性。对于不重要的逻辑,可以忽略,好比发一个谈天消息。建议只管忽略,重试逻辑写起来很贫苦,而且容易出问题。详细可以参考“漫衍式事务”相关信息。
在游戏的大部门的模块间耦合还是比力重的,所以skynet将集群认为是一个整体,我以为是合理的,所以不应该过份解耦。只有一些相对独立的模块,可以通过解耦防止问题扩散和雪崩。引入超时后,应该将游戏系统举行支解,焦点业务不使用超时,否则写超时处置惩罚逻辑会很是贫苦。非焦点业务加入超时,将焦点业务和非焦点业务举行解耦。
9 部门数据转存redis大部门游戏都独霸久化数据存在mysql或者mongo中。而redis常用于cache等场景,比力少用于持久化存储。但redis自己支持RDB和AOF持久化,其实有作为持久化存储的能力。
而有些游戏数据很小,但存在mysql内里贫苦。好比玩家的挚友关系数据,一个挚友关系涉及两个玩家,存在任何一个玩家身上都不合理。而如果存在mysql内里,如果设计欠好,可能加载时需要会见许多次mysql。
这类数据存在redis就很利便,占用不了几多空间,而且大大提高了会见速度。我们游戏千万量级的注册玩家,玩家的挚友关系数据也不外小几十G。一般来说,业务上存mysql/Mongo以为比力贫苦,数据量又不大,会见频率很高的,都可以存在redis中。
将Redis作为持久化存储其实是没有数据可靠性保证的,所以需要思量异常问题对游戏系统的影响。若系统不能接受任何的异常情况,建议还是使用mysql。此外,还需要思量回档问题(虽然永远不希望遇到)。
因为一个玩家的数据疏散在了差别的地方,有的在mysql,有的在redis,所以回档的时候要想措施回档到一个点。(阿里云的企业版Redis也就是Tair,支持精准时间点恢复数据)10 灰度测试情况对于一个线上项目,任何的修改都是有风险的,而有些底层的修改(好比数据存储相关代码)可能会涉及到所有的业务逻辑。
这种情况若只是让QA测试某些情况其实是很是不稳的。因此,我们将某些玩家逻辑历程设为灰度情况,只有指定的玩家可以进入。这样,我们就可以将某些涉及规模较大的改动,先在灰度情况中上线,选取某些玩家进入。
纵然泛起问题,也只影响选区的测试玩家。测试一段时间后,若测试玩家没有反馈问题,就可以将改动正式上线了。灰度情况是线上情况,和测试服具有本质区别。因为直接承载线上玩家,所以应用场景和测试服相比限制更多,好比我们只应用于玩家小我私家逻辑节点,也只测试底层代码逻辑,不测试业务逻辑。

和测试服比起来优点是比力灵活,不需要部署测试服而且摆设玩家进来测试。我们的灰度情况可以分为多级,好比第一级灰度只能公司内部测试人员进入,新功效刚开始上线时就先放到这个情况。第二级灰度我们在线随机选取几百到几千的玩家进入,一般是经由第一级灰度验证过的功效。
灰度测试第一级灰度情况的业务逻辑可以和线上有些许差异,可是第二级灰度因为直接面向外部玩家,所以要求业务上完全一致,一般都是底层的修改。一级灰度因为只有内部玩家,所以理论上来说可以随时重启更新代码,所以可以随时将代码上线测试,不用等周版本,比力灵活。一级灰度另有一些特殊用法,好比线上某个运动出了问题暂时关闭了入口,然后通过热更修复了。
为了验证线上的修复效果,可以先在灰度情况打开入口,验证修复效果。总之,有了灰度测试情况,可以相对大规模的验证一些底层修改,对于线上项目很是重要。
而且,可以比力灵活的在线上做一些事情。11 压测一款游戏上线前应该经由比力详细的压测,而且在后续的开发新功效和架构迭代历程中需要连续的举行压测。压测主要是为了评估三个内容:验证在大规模并发请求的情况下逻辑执行的正确性。
查找在大规模并发请求的情况下功效的性能瓶颈和性能热点。评估游戏或功效的承载能力和需求,计划机械部署需求。压测中需要关注的功效点(常泛起性能问题的场景):开服:关注登陆和建立账号,这两块逻辑一般都比力庞大。可以增加排队系统处置惩罚这个问题。
广播:好比全服谈天。可以分频道,也可以服务降级。
MMO游戏中玩家聚集:好比国战类游戏中的同屏大量玩家聚集。可以优化同步计谋,也可以逻辑分线。定时(同时)功效:好比某个运动会同时拉大量玩家进入某个场景。
单点服务:最多只能跑满一个CPU的服务。数据上限:好比某游戏曾经因为大量玩家申请某头部主播挚友,导致主播挚友申请列表增加了近10w,导致机械直接卡死。数据库相关:思量数据库的承载。全服玩家操作:好比通过下令给全服玩家发邮件。
为了利便压测,我们做了一套压测工具,可以支持在容器中快速部署压测集群、执行压测任务并汇总压测效果。12 动态扩容和缩容对于大部门游戏,都市有玩家在线人数的颠簸,好比某些运动期间人数许多,但逐日破晓都人数比力少。我们游戏周末晚上会搞一些运动,周末晚上运动期间宁静时相同时间段相比同时在线上升一倍。
如果我们根据最大同时在线部署机械,会造成较大的浪费。好比下图,常驻机械承载可以满足平时的需求,可是到了某些运动期间,就无法满足需求。这时候,如果支持动态扩容,就可以将机械在运动前增加,运动后接纳,既节约了成本,又给玩家更流通的游戏体验。
动态扩容缩容我们游戏可以将玩家小我私家逻辑和战斗逻辑历程做到了动态扩容缩容,这类历程占比最大性价比最高,其他历程没有支持。动态扩容缩容需要注意一些点:对于我们这种大DAU游戏,阿里云在某些可用区的备用库存不够,导致无法启动动态机械。所以需要思量跨可用区的支持。
动态扩容比力容易,动态缩容需要做一些逻辑处置惩罚,需要到达优雅退出的效果。战斗服比力容易,战斗竣事后关闭历程即可,对于我们这种玩家小我私家逻辑历程需要处置惩罚的事情多一些。我们关历程时会分步执行,先将此历程标志为新玩家不行进入,过段时间后再将非战斗状态的玩家踢下线(此步骤玩家无感知),最后强制踢下线所有玩家(此时玩家已经少少),基本做到了玩家无感知。
需要有较好的运维流程支持自动化,手动做的话人力成本太高而且容易堕落。最佳的方案是凭据线上的情况(好比在线玩家)自动化扩容缩容。
这个方法不适适用于自建机房,对于阿里云/AWS这种按量付费机械支持的较好的云提供商比力适合。13 cache大部门性能问题都可以通过cache来解决,空间换时间,多买点内存,让玩家玩的爽一点,很值。增加cache,需要思量两个点:cache存放位置和cache更新计谋。
13.1 cache存放位置常见的存放cache的位置有:贴近读取数据的实体(消费者)贴近生产数据的实体(生产者)生产者和消费者之间第三方,好比redis假设一个场景:玩家需要去拉取全服的一个排行榜,而这个排行榜的盘算可能是很重度的盘算,所以每次拉取都重新盘算不行取。服务端架构如下图所示,全服排行榜卖力盘算生成排行榜,每个玩家历程中治理许多个玩家entity,每个玩家都市去全服排行榜中请求排行榜信息。上面说的四种位置,在这个场景下的对应关系如下:贴近消费者:存在玩家entity中,每个玩家都有自己的cache。
贴近生产者:存在全服排行榜,cache全服有效,所有的玩家共享cache。消费者和生产者之间:存在玩家历程中,每个玩家历程中的所有玩家共享cache。差别玩家历程之间的玩家不共享。
redis:将生成的排行榜数据存在redis,全服玩家共享。说一下四种存放位置的优缺点和应用场景:贴近消费者:若消费者消费频率特别高,且差别消费者数据差别,可以存在消费者这边。这种情况其实比力少。
贴近生产者:这种情况比力多,一般是为了通过空间换事件,是常见的方案。消费者和生产者之间:这种情况一般是全部消费者的整体消费频率特别高,为了防止给单点压力太大,所以存在中间,降低压力。redis:这个和贴近生产者差不多,最大的区别在于,redis可以与服务器解耦,服务器重启,redis的数据也存在。
常见的情况好比存玩家的简要信息(供其他玩家检察)。固然,cache也可以在差别的地方同时存在,也就是多级cache。这种情况一般可以获得更好的效率,但需要针对每一级cache界说维护和更新计谋,逻辑越发庞大,bug更难查。
13.2 cache更新/失效计谋cache的引入一般是为相识决性能问题,但也并不是没有成本。成本就在于需要治理cache,也就是决议cache什么时侯失效和更新,增加了编程的庞大性。生存时间(ttl,time to live)cache最常见的更新计谋是使用生存时间ttl,即缓存凌驾一定的时间后自动失效,然后重新盘算或者去数据源拉取。
好比域名剖析中就是用ttl控制DNS服务器中域名剖析信息缓存失效。这种计谋最简朴,建议优先使用这种计谋。主动更新cache这种计谋是cache的生产者主动去更新cache,这种更新计谋思想类似写扩散。
好比游戏常见的玩家简要信息cache,这种cache一般是玩家更新自己的信息时,就去更新自己的简要信息。(固然,纷歧定完全实时)这种计谋一般是要求cache的实时性要求比力高,可是又不希望所有的请求都打到数据生产者中执行。关于这类思想,大家可以去搜索“读扩散/写扩散”来相识更多的内容。
牢固cache空间某些场景下,cache可用的空间是有限的, 在有限空间的前提下,我们希望只管的提升cache空间的使用效率。当可用空间没有用尽时,cache一直不会失效,当可用空间用尽后,以一定的计谋去将某些cache失效,以获得空间给新的cache。最常见的是LRU计谋。
因为硬件资源是有限的,这种计谋也常见于硬件和系统层,好比虚拟内存的治理,好比mysql等数据库将部门信息缓存在内存中以提高查询效率,好比Redis内存空间用尽后内存淘汰。这种cache的治理方式业务逻辑中用的比力少,偶然配合其他计谋一起使用,增加保底机制防止cache所占用的内存空间过大。常见的计谋有LRU和LFU。好比若redis占用内存靠近内存上限时,会使用类LRU计谋淘汰数据。
其他各种计谋cache也可以凭据差别的业务场景设置更新和失效计谋,好比可以在一个副本中将某些cache设为永不失效,只有在副本竣事时才去统一清理。详细计谋凭据详细需求可以使用种种花式方案。
后记一款DAU百万级的游戏,而且是已经上线的游戏,其实优化起来很是难题,真*为一辆高速行驶的汽车换零件。为了给玩家带来更好的游戏体验,我们做优化计划时并不守旧,但很是审慎的执行。如临深渊,如履薄冰。
附:公司招人,在杭州,一线薪水,不输任何其他游戏公司。公司快速生长中,时机多多!服务端、客户端都要,技术专家、主程都要~投简历请发 yangpengwei@pandadastudio.com。
本文关键词:爱游戏app下载,某,百万,DAU,游,戏的,服务,端,优化,事情,文
本文来源:爱游戏app下载-www.dx-magnet.com