WangShuXian6 / blog

FE-BLOG
https://wangshuxian6.github.io/blog/
MIT License
46 stars 10 forks source link

使用 C++ 和 Unreal 的 MMORPG 游戏开发系列]第 4 部分:游戏服务器 #208

Open WangShuXian6 opened 2 weeks ago

WangShuXian6 commented 2 weeks ago

[使用 C++ 和 Unreal 的 MMORPG 游戏开发系列]第 4 部分:游戏服务器

学习网络/多线程/操作系统等核心专业知识, 这是一门可以从头开始构建游戏服务器并学习 MMORPG 技术的课程。 新的服务器程序员需要了解所有的一般知识 无论您加入哪个项目,您都将拥有适应的基础知识,而不会惊慌失措。

部分 1. OT

3个 ∙ (48分钟)

部分 2. 多线程编程

24个 ∙ (10小时 1分钟)

部分 3. 内存管理

10个 ∙ (5小时 50分钟)

部分 4. 网络编程

12个 ∙ (6小时 3分钟)

部分 5. 网络库制作

10个 ∙ (6小时 7分钟)

部分 6. 数据包序列化

9个 ∙ (5小时 45分钟)

部分 7. JobQueue

7个 ∙ (3小时 55分钟)

部分 8. 数据库连接

5个 ∙ (3小时 10分钟)

课程发布日期: 2021. 06. 10.
最后更新日期: 2021. 06. 11.


# 部分 1. OT

3个 ∙ (48分钟)

## OT 11:55  
## 服务器 OT 09:50  
## 环境设置 26:36  

# 部分 2. 多线程编程

24个 ∙ (10小时 1分钟)

## 多线程概论 13:32  
## 线程创建 21:13  
## 原子操作 17:53  
## 锁基础 22:18  
## 死锁 24:32  
## 锁实现理论 13:49  
## 自旋锁 24:34  
## 睡眠 17:35  
## 事件 25:34  
## 条件变量 18:45  
## Future 33:26  
## 缓存 14:45  
## CPU 管道 19:48  
## 内存模型 44:50  
## 线程局部存储 15:53  
## 基于锁的栈/队列 17:44  
## 无锁栈 1 20:42  
## 无锁栈 2 24:44  
## 无锁栈 3 35:20  
## 无锁队列(选修课程:难度较高,请注意) 42:54  
## 线程管理器 22:37  
## 读写锁 44:04  
## 死锁检测 52:24  
## 练习题 13:03  

# 部分 3. 内存管理

10个 ∙ (5小时 50分钟)

## 引用计数 43:17  
## 智能指针 31:16  
## 分配器 25:25  
## Stomp 分配器 41:57  
## STL 分配器 19:22  
## 内存池 1 37:11  
## 内存池 2 50:49  
## 内存池 3 14:38  
## 对象池 25:23  
## 类型转换 01:00:42  

# 部分 4. 网络编程

12个 ∙ (6小时 3分钟)

## 套接字编程基础 1 14:50  
## 套接字编程基础 2 45:17  
## TCP 服务器实习 31:18  
## TCP 与 UDP 19:55  
## UDP 服务器实习 22:38  
## 套接字选项 21:17  
## 非阻塞套接字 22:24  
## Select 模型 31:02  
## WSAEventSelect 模型 38:38  
## 重叠模型(事件驱动) 46:16  
## 重叠模型(回调驱动) 31:36  
## 完成端口模型 38:06  

# 部分 5. 网络库制作

10个 ∙ (6小时 7分钟)

## Socket 工具 35:54  
## IocpCore 58:36  
## 服务器服务 45:02  
## 会话 1 32:45  
## 会话 2 23:17  
## 会话 3 22:42  
## 接收缓冲区 27:12  
## 发送缓冲区 41:13  
## 发送缓冲池 38:41  
## 数据包会话 41:40  

# 部分 6. 数据包序列化

9个 ∙ (5小时 45分钟)

## 缓冲区助手 27:58  
## 数据包处理器 31:52  
## Unicode 35:07  
## 数据包序列化 1 37:08  
## 数据包序列化 2 23:40  
## 数据包序列化 3 34:41  
## Protobuf 56:25  
## 数据包自动化 1 41:52  
## 数据包自动化 2 56:58  

# 部分 7. JobQueue

7个 ∙ (3小时 55分钟)

## 聊天实习 45:19  
## JobQueue 1 30:15  
## JobQueue 2 38:02  
## JobQueue 3 32:53  
## JobQueue 4 22:50  
## JobQueue 5 32:15  
## JobTimer 33:35  

# 部分 8. 数据库连接

5个 ∙ (3小时 10分钟)

## 数据库连接 56:28  
## 数据库绑定 41:26  
## XML 解析器 30:59  
## ORM 27:36  
## 过程生成器 33:36  

**课程发布日期**: 2021. 06. 10.  
**最后更新日期**: 2021. 06. 11.
WangShuXian6 commented 2 weeks ago

部分 1. OT

3个 ∙ (48分钟)

OT 11:55

欢迎来到使用C++和Unreal进行MMORPG游戏开发系列的第四部分

这一部分将特别关注游戏服务器的开发。你应该具备C++的基本知识,了解一些SQL或Python的知识会对你有帮助,虽然这并不是必需的。从这一讲开始,难度会显著增加。因此,我将目标受众大致分为两类:服务器程序员和求职者。这些人包括在游戏学院学习的学生,以及那些希望将服务器知识融入他们最终作品集的学生,还有对服务器知识感兴趣的客户端程序员。这门课程就是为他们准备的。

注意事项

鉴于内容的复杂性,对于那些对C++技能不自信的人来说,跟上进度可能会很有挑战性。这是需要记住的一点。

什么是游戏服务器?

游戏服务器本质上是一个程序,它通过充当中介来促进在线多人游戏。它管理MMORPG世界中的所有内容,包括:

服务器还作为控制者,将游戏世界中的信息传递给客户端。虽然理论上很简单,但实际上,实现服务器是一个非常具有挑战性的领域。

学习目标

在总结之前,我将简要回顾一下通过这门课程你将学到的知识。

项目运行状态和用户交互

现在,如果我们看看我们完成项目的运行状态,似乎我们还没有将Unreal Engine完全整合,以便看到显著的图形输出。所以,这个项目看起来并没有什么特别令人印象深刻的地方。

用户连接情况

目前,大约有500名用户连接到服务器,加入同一个房间,以练习相互之间广播“Hello World”。尽管客户端断开连接,我们可以确认服务器能够安全处理这些情况而不会崩溃。因此,从表面上看,它可能看起来只是一个基本的聊天程序,但在这个过程中,我们学到了很多东西。

编程和内存管理的深入学习

总结一下我们覆盖的内容,我们首先探讨了与线程相关的主题。尽管在我们的服务器引擎中没有很多类,但我们涵盖了C++标准中包含的大量内容。

线程相关主题

我们学习了如何创建线程,什么是原子类型,锁的本质,以及实现锁的各种方法。我们还探讨了死锁的原因,并进行了实践练习,尝试了自旋锁、休眠和基于事件的方法,然后研究了标准中引入的条件变量和未来。

TLS与数据结构

接下来,我们简要介绍了TLS,练习使用锁创建基于栈的数据结构,并致力于实现无锁栈和队列。

网络编程与数据库集成实践

接下来,我们讨论了线程管理,创建了一个死锁探查器,以快速检测调试场景中的死锁,并探索解决这些问题的各种方法。在完成线程相关的主题后,我们转向内存管理。

内存管理的实践

我们没有使用基本的new和delete方法,而是研究了如何实现自定义的内存管理分配器。我们创建了不同的分配器,例如Stomper分配器,以100%概率捕获内存损坏。

内存池与对象池化

然后,我们转向内存池,应用池分配器以确保自动内存管理,并实现对象池化。我们还探索了快速使用的类型转换概念,而不是dynamic_cast,我们也进行了实践。

网络编程细节

接下来,我们进入了第三部分,即网络编程。我们介绍了网络编程的概念,并为套接字编程奠定基础,研究了TCP和UDP的概念,随后进行了实践练习。

网络I/O模型

我们练习了使用阻塞和非阻塞套接字以及各种网络I/O模型。然后,我们开始使用IOCP模型开发网络库,成功确认它可以处理数百或数千个用户的连接和断开而不会出现问题。

数据包序列化与自动化

之后,我们全面讨论了数据包序列化。我们探讨了数据包序列化的定义及其相关技术,随后进行了实践练习。我们还与Google创建的协议缓冲区进行了集成,并确认连接正常。

自动化代码创建

接下来,我们创建了自动化代码,以使用多种方法简化我们的内容工作。结果,目前这些代码正在自动处理。通过对协议文件进行细微调整和重新构建,我们还确认了客户端数据包处理程序可以重新生成。

自动化技术探讨

我们深入研究了实践中常用的自动化技术,并在总结数据包序列化后,讨论了为何我们采用基于作业的方法而非基于锁的方法,以及与作业相关的队列创建中遇到的问题和解决方案。

数据库集成实践

最后,我们进行了数据库集成的实践练习。我们不仅仅是使用Orbit连接到数据库;我们还探索了通过创建包装类来方便管理数据库的各种技术。

数据库版本管理

我们关注了数据库版本管理的问题,而不仅仅是通过代码来管理数据库。我们还研究了如何使用XML来简化版本控制。在这种情况下,例如,如果我们要添加一列,我们可以看到重建后,自动化代码将允许我们轻松管理数据库。

结语

如果你理解了整个过程,你将学到任何服务器程序员应该知道的所有基本知识,无论项目是MMORPG还是其他任何项目。这些基础知识将帮助你轻松适应任何项目。

有了这些,我们已经覆盖了很多材料,我鼓励你再次回顾整个过程。我希望这些信息将对你未来的学习大有裨益。

我已初步查看了将要学习的主题,并且在创建这次讲座时,我也回想起了自己的经历。我对在线游戏充满热情,如果我能从事游戏行业,我肯定会想成为一名服务器程序员。然而,当我开始研究服务器时,我发现几乎没有相关材料可供参考。我努力寻求帮助,购买了所有看起来稍微相关的书籍。

服务器 OT 09:50

在今天的第一次会议中

我准备了一个关于服务器的简单介绍。如果你观看过我的C#课程,你会注意到一些相同的内容会再次出现。然而,可能有些人没有参加C#课程,第一次接触服务器概念。因此,让我们简要回顾一下什么是服务器。

服务器的定义

自从我开始作为服务器程序员的职业生涯以来,我收到了一些常见的问题。很多人表达了学习服务器的愿望,但不知从何入手,提到缺乏共享的信息。我还收到了公司请求推荐学习Linux服务器书籍的请求。然而,我注意到,与客户端不同的是,虽然有许多学院和一些可用的书籍,但人们对服务器似乎有很多困惑。

常见的困惑

例如,在谈论学习Linux服务器时,通常不清楚我们是指Web服务器、游戏服务器,还是仅仅是服务器管理。这造成了模糊性。通常,人们认为服务器是深奥、困难和神秘的。当我们想到服务器时,我们想象的是充满昂贵设备的服务器机房。然而,在典型的客户端-服务器模型中,服务器的概念并没有那么复杂。

客户端与服务器

基本上,服务器就像我们的客户端,指的是在计算机上运行的程序。区别在于,服务器是一个始终运行并等待与其他计算机连接的程序。虽然我们有时会将计算机本身称为服务器,但我想澄清,在游戏的上下文中,我们具体讨论的是在该计算机上运行的程序。

比喻

我在讲座中常用的一个比喻是,客户端编程很像拍电影,而服务器编程则类似于经营餐厅。因此,如果我们将经营餐厅作为一个类比,首先需要打开餐厅以欢迎顾客,然后随时准备为他们服务。你显然无法预测顾客何时会到来,但当他们到来时,你要很好地引导他们,并根据菜单和政策提供服务。这基本上就是餐厅的概念,你可以将服务器的运作视为非常相似的方式。

服务器的类型

我们可以将服务器分为两种主要类型:Web服务器游戏服务器。尽管“游戏服务器”并不是一个正式术语,但它在游戏行业中被广泛使用,指的是这种类型的服务器。

Web服务器

餐厅的类型也各不相同。例如,有专注于外卖或包装的餐厅,如麦当劳,虽然在韩国并不常见,但在美国有自取窗的选项,你可以快速取餐并离开。你可以将Web服务器视为类似的概念。在这种情况下,餐厅为那些取餐后立即离开的顾客服务,创造了一种接触丧失的情况——更像是问答式的互动。

游戏服务器

另一方面,游戏服务器可以类比为典型的餐厅体验。因此,当我们谈论一个典型的餐厅时,不只是收到菜单后立刻离开;通常,你会被安排座位,服务人员可能会来询问你的偏好或接受额外的订单,创造了员工与顾客之间的实时互动。

服务器分类的重要性

那么,为什么我们需要以这种方式分类服务器呢?服务器的选择实际上取决于特定时刻的需求。对于Web服务器,它们特别适用于信息很少请求和更新的情况。在不需要实时互动的情况下,Web服务器无疑是更好的选择。然而,缺点是,在餐厅环境中,员工不能首先接近顾客。这意味着一旦顾客下单并领取食物,他们往往会立刻离开,使得很难了解顾客的状态。

Web服务器的特点

此期间,随着理解的进展,顾客的状态将被遗忘,直到下次访问,这就是为什么Web服务器常被称为无状态服务器。另一方面,Web服务器开发并不局限于游戏;它主要用于创建Web服务。例如,技术经常应用于Naver、亚马逊和谷歌等网站的开发。因此,在使用Web服务器时,几乎没有从头开始的情况;相反,你通常会根据编程语言选择一个框架。

各语言框架

在C#生态系统中,有ASP.NET;在Java中,有Spring;在JavaScript中,有Node.js。每种语言都有其自己准备好的框架。

游戏服务器的需求

相比之下,当涉及到游戏服务器时,它们在请求和更新数量高且需要实时通信的情况下是必需的。员工必须随时能够接近顾客以进行检查,而在顾客在场时,还应监控其他顾客的状态以提供优质服务。这表明在这种情况下存在状态。

实时互动

因此,当我们想到在线游戏时,不仅仅是发送消息然后结束;我需要控制我的角色以确保与其他用户的体验一致。这意味着,与Web服务器不同,必然会有高频率的请求和更新。

复杂性与挑战

然而,创建游戏服务器常常被视为充满神秘和复杂性。在客户端的情况下,如果你学习Unity或虚幻引擎,即使你不完全理解内部运作的方式,你仍然可以创建出不错的游戏。另一方面,尽管有许多知名的服务器引擎,但仅仅学习引擎并使用它而没有任何先前知识并不那么简单。

游戏类型的影响

需求会根据游戏类型显著不同;例如,无论是回转寿司餐厅、五花肉店、酒店自助餐,还是汤店,都会决定菜单。如果菜单不同,餐厅的内部和所需员工数量就不能相同。同样,在在线游戏中,需求可能会根据游戏是MMORPG、移动类型、第一人称射击等而大相径庭。

未来的研究方向

总结一下我们今后需要研究的内容,当经营一家餐厅时,我们必须考虑顾客容量。例如,如果这是一个多个顾客共享一个房间的餐厅,我们需要确定可以容纳多少人。此外,如果我们决定雇用员工,就必须考虑如何分配他们以及雇用多少人。

关键考虑因素

有许多因素需要考虑,游戏服务器也是如此。例如,我们需要确定最大并发玩家数、游戏类型、响应时间是否可以稍微慢一点、如果使用线程如何分配、网络模型将是什么,以及如何处理数据库等关键考虑因素。

结束语

因此,随着我们在这个项目中的推进,我们的目标是研究MMORPG技术。这意味着我们将涵盖多设置、网络数据库、游戏逻辑、服务器架构等重要主题。通过学习这一部分,你将对游戏服务器的运作有基本的理解。在了解客户端后,我们将进行整合,为未来创建一个令人信服的MMORPG奠定基础。至此,让我们结束对服务器概念的初步概述。

环境设置 26:36

游戏服务器环境设置

今天我开始重新研究游戏服务器的旅程。在第一节课中,我将创建一个简单的环境设置项目并开始。使用的版本是 Visual Studio 2019,但我假设观看这个讲座的人都有一些编码经验,所以我会跳过 Visual Studio 的安装。

创建项目

  1. 创建控制台应用程序

    • 进入“创建新项目”。
    • 设置一个控制台应用程序,指定位置为创建的名为“cpp server”的文件夹。
    • 解决方案命名为“Server”,项目命名为“Game Server”。
  2. 添加客户端和核心项目

    • 右键单击解决方案,选择“添加新项目”,创建一个控制台应用程序,命名为“Dummy Client”。
    • 再次右键单击,添加新项目,创建一个静态库,命名为“Server Core”。

整理文件结构

输出目录设置

  1. 右键单击项目,选择“属性”。
  2. 设置输出目录为所有配置,并为每个模式(调试/发布)设置不同的路径。

Server Core 项目设置

添加功能

总结

通过以上步骤,我们创建了一个基础的游戏服务器项目结构,接下来可以在 Server Core 中添加更多功能,并在游戏服务器和 Dummy Client 中引用这些功能。希望这个排版能帮助你更好地理解和使用这些步骤!如果需要进一步的帮助,请随时告诉我!