01navmesh寻路与漏斗算法
多边形寻路参考PolygonNavMesh 原理:
1. 将unity导出的数据生成凸多边形
2. 找出所有凸多边形共享的边
3. 使用A*算法找出起点到目标点所经过的多边形列表
4. 使用漏斗算法找出顶点坐标
02游戏服务端究竟解决了什么问题?
整理下这篇文章到目前为止做了什么事情:
在文章的一开始确定了游戏服务端要解决的核心两个问题:消息的pipeline与游戏世界状态维护。
通过回顾历史的形式提出游戏服务端中最常见的需求情景:多玩家场景同步,并梳理了场景同步最适合的消息pipeline。
结合切场景的扩展需求,提出Gate这种基础设施抽象(infrastructure abstraction,简称IA)。
尝试进行高内聚、低耦合的服务划分,并总结Gate无法兼顾的消息pipeline。
针对Gate无法处理的消息pipeline(service -> service),提出新的MQ-IA,可以大大简化服务间拓扑关系。基于不同的IA与相关协议,提出更高层次的RPC协议,定义了适合.Net2.0和.Net4.5的两种异步RPC调用规范。实现了不同IA到统一规范的Adaptor。
总结了游戏中RPC应用的pattern,不同pattern如何与不同IA结合使用。同样通过回顾历史的形式引入数据服务来取代传统MMO中的Db代理进程。
结合MQ与数据服务,提出无状态服务在游戏服务端中的应用情景,展开介绍数据服务对于无状态服务的意义所在。
基于构建全局数据服务的理念,尝试实现一种多实例的、每实例内向不同服务提供原子修改操作级别一致性的数据服务。
为数据服务增加了符合需求的高可用支持。引入了zookeeper,可以让普通的服务也可以复用同样的协调者组件。
总结下出现的几种概念:
IA。包括Gate、MQ、内存db、持久化强一致性db、分布式协调器等等。不同的IA各司其职,各自只负责解决分布式系统中的一小部分问题。
RPC与Pattern。面向应用层的统一服务调用方式与规范。
Adaptor。不同的IA与相关协议到统一RPC与Pattern的适配器。
03Recast & Detour 寻路引擎的基本流程
Recast & Detour是一个开源的寻路引擎,其遵循zlib协议,基本上你可以免费且无限制的将它用作个人和商业产品中。
从名字中我们可以看到,这个引擎分成两部分:
第一部分是Recast,主要功能是将场景网格模型生成用于寻路的网格模型(Navigation Mesh)。所生成的寻路网格模型当然要比原模型简单很多,这也提高了实时寻路算法的效率。
第二部分是Detour,主要功能是利用上一步所生成的Navigation Mesh进行寻路,其包含了多种寻路算法,根据不同的路径光滑程度与寻路时间效率的要求可做不同的选择。

04龙之谷服务器设计
9月23日,首届“梦想·匠心”腾讯游戏开发者大会于深圳举行,在技术分论坛上,盛大游戏《龙之谷》手游技术总监李阳分享了龙之谷的服务器设计。作为《龙之谷》的手游技术负责人,李阳从事多年游戏后端开发,参与多款上线项目研发。李阳于本次论坛上分享《龙之谷》手游服务器在架构设计、灾备处理、性能优化、压力测试等方面遇到的一些问题和经验总结。05pbc的一个陈年老BUG
这里就得提到pbc的两个feature。第一个是,如果一个optional字段的数据不存在,那么你尝试去读的时候,会返回一个默认值。这个默认值的话如果协议里不定义,整数是0,字符串是空串,而table就会生成一个新table,里面的数据全是默认值。
第二个是,如果某个optional的字段的内容是默认值,那么打包的时候会忽略。也就是说pack的结果的二进制里什么也没有。
说它是两个feature是因为,原生的protobuf是没有这回事儿的。二进制里没有,unpack的结果里去读也不会有;有数据但是是默认值,打包的二进制里也会有key-value,只是value是默认值(0或者空串),默认值一般都很小。
然后既然要自己动手,就得去读代码了。对以上features的实现,特别是读取不存在的数据的实现,并且为了高效pbc采用了默认值table的方法。什么叫默认值table呢?就是每一个protubuf的message,在第一次解包的时候,pbc的lua-binding都会生成一个默认值的table。
假设某个要读取的数据不存在,pbc的lua-binding会返回这个默认值的table。举个例子:
local msg1 = pbc.unpack('abc', buffer1)
-- 假设这时候nodata这个数据不存在
print(msg1.nodata.int_type)
-- 假设0是默认值,这里会输出0
local msg2 = pbc.unpack('abc', buffer2)
-- 如果buffer1和buffer2里都没有nodata的数据,下面两行会输出同一个table
print(msg1.nodata)
print(msg2.nodata)
那么问题就来了,这种情况,如果对解包数据是只读还好,一旦进行了写入,假设执行了msg1.nodata.int_type = 100,那么msg2.nodata.int_type也变成了100,并且以后解包的这个message的空数据里的nodata.int_type都变成了100。这也是最开始提到的那个BUG的原因。
06Lua查找表元素过程(元表、__index方法是如何工作的)
举个栗子:)
father = {
house=1
}
son = {
car=1
}
setmetatable(son, father) --把son的metatable设置为father
print(son.house)
输出的结果是nil,但如果把代码改为
father = {
house=1
}
father.__index = father -- 把father的__index方法指向自己
son = {
car=1
}
setmetatable(son, father)
print(son.house)
输出的结果为1,符合预期

07检测Lua中临时对象造成的内存增长
创建临时对象,比如临时表、临时闭包,向table里加key value,都会使lua虚拟机内存增加,虽然可被gc掉但会造成更频繁的gc,gc速度没分配速度快的话进程容易挂。问题就是如何自动化的找到分配临时对象内存的lua代码,造成内存增长的情况很多怎么找呢
08Lua math string库
Lua math string 库 http://cloudwu.github.io/lua53doc/contents.html 《Lua5.3参考手册》
09pbc默认值问题
这里就得提到pbc的两个feature。第一个是,如果一个optional字段的数据不存在,那么你尝试去读的时候,会返回一个默认值。这个默认值的话如果协议里不定义,整数是0,字符串是空串,而table就会生成一个新table,里面的数据全是默认值。
第二个是,如果某个optional的字段的内容是默认值,那么打包的时候会忽略。也就是说pack的结果的二进制里什么也没有。

10浅析Lua中table的遍历和删除
在Lua中,最最核心的数据结构就是表.表不仅可用作数组,还可以用作字典.Lua面向对象的实现也是用表实现的.这里主要讨论表的遍历和删除操作
11Lua非常有用的工具——递归打印表数据
在Lua中,我认为最最核心的数据结构就是表。表不仅可用作数组,还可以用作字典。Lua面向对象的实现也是用表实现的
12quick3.3下集成云风pbc(windows版)
protocolbuffer(以下简称PB)是google 的一种数据交换的格式,它独立于语言,独立于平台。google 提供了多种语言的实现:java、c#、c++、go 和 python,每一种实现都包含了相应语言的编译器以及库文件

点击排行

站长推荐

猜你喜欢
站点信息
- 建站时间:2016-04-01
- 文章统计:728条
- 文章评论:82条
- QQ群二维码:扫描二维码,互相交流
