草庐IT

三种同步方式:状态同步、帧同步、状态帧同步

一天一个Unity小知识 2023-03-28 原文

以下内容只是在学习和工作中的一些小见解,希望不足之处能得到大家的指正,也希望能对刚刚准备入行游戏的小伙伴有一点帮助。

 

首先我们默认大家已经了解了网络收发机制,如果有需要,后面再补充。

 

 状态同步:敌不动,我不动

 

对于状态同步而言,简单的说就是当游戏世界中的玩家没有进行操作或者移动的时候,我们认为游戏世界里大家都没有操作,服务器除了一般的心跳检测之类的,不会对客户端下发任何数据进行同步。

当某个客户端进行了某个操作后,操作发送到服务器,服务器将玩家的操作执行出结果,得出玩家现在的快照(位置、血量、蓝量等等变化的信息),再由服务器将该客户端的信息广播下发到其他的客户端进行同步,当然服务器为了防止作弊也是有做验证机制的。

也就是说状态同步就是将逻辑放在了服务器,而客户端更像一个显示器,游戏世界玩家没有属性变化,基本不会进行同步消息下发。

 

帧同步:你们和我这样做


帧同步的概念其实更加简单,每个客户端都在执行相同的操作,所以最后的结果一样。

从上面的话中不难猜出,帧同步的逻辑是放在每一个客户端的,客户端将操作发送给服务器,服务器按照固定的时间内收集操作,然后将这个固定时间内收集的所有操作打包再进行转发给每个客户端后再进行下一次收集,所有客户端再通过服务器下发的操作执行逻辑,就是最初级的帧同步概念,当然服务器也可以执行逻辑进行验证操作防止作弊。

我们所谓的帧理解为一次逻辑的更新时间,就有点类似FixedTime一样,是一个固定的时间。

举个栗子:某者某耀Moba类型游戏,就是15帧的刷新率,也就是它将1秒分成了15次的逻辑更新,你所看见的60-90多帧只是表现帧数,表现帧数越高越丝滑。

还有就是需要使用定点数,当你的逻辑中使用了浮点数的时候,因为每一台机器的不同,浮点最后的有效值其实是不一样的,所以为了保证逻辑的同步性,再游戏逻辑中,需要使用定点数。

大多数帧同步的逻辑是只放在每个客户端的,无论是否有操作,每一帧都会有服务器数据下发。

 

状态帧同步:每时每刻知道你在哪儿

 

状态帧同步就是状态同步和帧同步的概念相结合。客户端向服务器上传操作,服务器跑逻辑,但是又在按照固定的每一帧下发所有玩家的状态(属性位置等)给每一个客户端实现同步。

这里最具典型的就是守望先锋就是采用的状态帧同步的概念。在这个概念中,服务器和客户端都是有一套相同的代码的,但是客户端的逻辑代码更偏向于用来做预测行为,客户端可以预测主玩家的行为,让主玩家不需要等待服务器的快照就能直接执行玩家按下的操作,这样就能增加玩家的体验,而当服务器下发快照的时候,玩家再去验证自己的预测是否正确,不正确的就对操作进行回滚。

 

每种同步方式都有自己的优劣,没有最好的同步方式,只有最合适的。在互联网高速发展的当下,我相信在不久的将来,或许会有很多新的同步解决方案等待大家的挖掘。

 

有关三种同步方式:状态同步、帧同步、状态帧同步的更多相关文章

  1. ruby - 在 Ruby 程序执行时阻止 Windows 7 PC 进入休眠状态 - 2

    我需要在客户计算机上运行Ruby应用程序。通常需要几天才能完成(复制大备份文件)。问题是如果启用sleep,它会中断应用程序。否则,计算机将持续运行数周,直到我下次访问为止。有什么方法可以防止执行期间休眠并让Windows在执行后休眠吗?欢迎任何疯狂的想法;-) 最佳答案 Here建议使用SetThreadExecutionStateWinAPI函数,使应用程序能够通知系统它正在使用中,从而防止系统在应用程序运行时进入休眠状态或关闭显示。像这样的东西:require'Win32API'ES_AWAYMODE_REQUIRED=0x0

  2. ruby - 如何以所有可能的方式将字符串拆分为长度最多为 3 的连续子字符串? - 2

    我试图获取一个长度在1到10之间的字符串,并输出将字符串分解为大小为1、2或3的连续子字符串的所有可能方式。例如:输入:123456将整数分割成单个字符,然后继续查找组合。该代码将返回以下所有数组。[1,2,3,4,5,6][12,3,4,5,6][1,23,4,5,6][1,2,34,5,6][1,2,3,45,6][1,2,3,4,56][12,34,5,6][12,3,45,6][12,3,4,56][1,23,45,6][1,2,34,56][1,23,4,56][12,34,56][123,4,5,6][1,234,5,6][1,2,345,6][1,2,3,456][123

  3. ruby - 解析 RDFa、微数据等的最佳方式是什么,使用统一的模式/词汇(例如 schema.org)存储和显示信息 - 2

    我主要使用Ruby来执行此操作,但到目前为止我的攻击计划如下:使用gemsrdf、rdf-rdfa和rdf-microdata或mida来解析给定任何URI的数据。我认为最好映射到像schema.org这样的统一模式,例如使用这个yaml文件,它试图描述数据词汇表和opengraph到schema.org之间的转换:#SchemaXtoschema.orgconversion#data-vocabularyDV:name:namestreet-address:streetAddressregion:addressRegionlocality:addressLocalityphoto:i

  4. ruby-on-rails - 跳过状态机方法的所有验证 - 2

    当我的预订模型通过rake任务在状态机上转换时,我试图找出如何跳过对ActiveRecord对象的特定实例的验证。我想在reservation.close时跳过所有验证!叫做。希望调用reservation.close!(:validate=>false)之类的东西。仅供引用,我们正在使用https://github.com/pluginaweek/state_machine用于状态机。这是我的预订模型的示例。classReservation["requested","negotiating","approved"])}state_machine:initial=>'requested

  5. ruby-on-rails - 正确的 Rails 2.1 做事方式 - 2

    question的一些答案关于redirect_to让我想到了其他一些问题。基本上,我正在使用Rails2.1编写博客应用程序。我一直在尝试自己完成大部分工作(因为我对Rails有所了解),但在需要时会引用Internet上的教程和引用资料。我设法让一个简单的博客正常运行,然后我尝试添加评论。靠我自己,我设法让它进入了可以从script/console添加评论的阶段,但我无法让表单正常工作。我遵循的其中一个教程建议在帖子Controller中创建一个“评论”操作,以添加评论。我的问题是:这是“标准”方式吗?我的另一个问题的答案之一似乎暗示应该有一个CommentsController参

  6. ruby - 字符串文字中的转义状态作为 `String#tr` 的参数 - 2

    对于作为String#tr参数的单引号字符串文字中反斜杠的转义状态,我觉得有些神秘。你能解释一下下面三个例子之间的对比吗?我特别不明白第二个。为了避免复杂化,我在这里使用了'd',在双引号中转义时不会改变含义("\d"="d")。'\\'.tr('\\','x')#=>"x"'\\'.tr('\\d','x')#=>"\\"'\\'.tr('\\\d','x')#=>"x" 最佳答案 在tr中转义tr的第一个参数非常类似于正则表达式中的括号字符分组。您可以在表达式的开头使用^来否定匹配(替换任何不匹配的内容)并使用例如a-f来匹配一

  7. ruby - Net::HTTP 获取源代码和状态 - 2

    我目前正在使用以下方法获取页面的源代码:Net::HTTP.get(URI.parse(page.url))我还想获取HTTP状态,而无需发出第二个请求。有没有办法用另一种方法做到这一点?我一直在查看文档,但似乎找不到我要找的东西。 最佳答案 在我看来,除非您需要一些真正的低级访问或控制,否则最好使用Ruby的内置Open::URI模块:require'open-uri'io=open('http://www.example.org/')#=>#body=io.read[0,50]#=>"["200","OK"]io.base_ur

  8. 【鸿蒙应用开发系列】- 获取系统设备信息以及版本API兼容调用方式 - 2

    在应用开发中,有时候我们需要获取系统的设备信息,用于数据上报和行为分析。那在鸿蒙系统中,我们应该怎么去获取设备的系统信息呢,比如说获取手机的系统版本号、手机的制造商、手机型号等数据。1、获取方式这里分为两种情况,一种是设备信息的获取,一种是系统信息的获取。1.1、获取设备信息获取设备信息,鸿蒙的SDK包为我们提供了DeviceInfo类,通过该类的一些静态方法,可以获取设备信息,DeviceInfo类的包路径为:ohos.system.DeviceInfo.具体的方法如下:ModifierandTypeMethodDescriptionstatic StringgetAbiList​()Obt

  9. 使用canal同步MySQL数据到ES - 2

    文章目录一、概述简介原理模块二、配置Mysql使用版本环境要求1.操作系统2.mysql要求三、配置canal-server离线下载在线下载上传解压修改配置单机配置集群配置分库分表配置1.修改全局配置2.实例配置垂直分库水平分库3.修改group-instance.xml4.启动监听四、配置canal-adapter1修改启动配置2配置映射文件3启动ES数据同步查询所有订阅同步数据同步开关启动4.验证五、配置canal-admin一、概述简介canal是Alibaba旗下的一款开源项目,Java开发。基于数据库增量日志解析,提供增量数据订阅&消费。Git地址:https://github.co

  10. ruby-on-rails - 为模型创建状态属性 - 2

    我想为我的Task模型创建一个status属性,该属性将按以下顺序指示它在三部分进度中的位置:打开=>进行中=>完成。它的工作方式类似于亚马逊包裹的交付方式:已订购=>已发货=>已交付。我想知道设置此属性的最佳方法是什么。我可能是错的,但创建三个独立的bool属性似乎有点多余。实现此目标的最佳方法是什么? 最佳答案 Rails4有一个内置的enummacro.它使用单个整数列并映射到键列表。classOrderenumstatus:[:ordered,:shipped,:delivered]end状态映射如下:{ordered:0,

随机推荐