ADB-02 分布式数据库

📅 预计 70 分钟 | ⭐ = 重要知识点 | 📌 中英术语见文末
📖 架构与协议概念为主,配文字分步推演


2.1 分布式数据库系统概念

一家开分店的连锁书店

想象一家连锁书店:最初只有总店一间,所有书都堆在里面,读者都要跑去总店借——这是集中式。后来它在不同城市开了分店,每家分店存一部分书,但借书卡全国通用,你在任何一家分店都能查到全公司的藏书目录,仿佛只有一座图书馆——书(数据)分散存放,但目录(逻辑)是统一的,这就是分布式数据库的雏形。

定义:物理分散,逻辑统一

分布式数据库系统(Distributed Database System,DDBS)= 分布式数据库(DDB)+ 分布式数据库管理系统(DDBMS)。核心定义八个字:

数据分散存储在多节点、逻辑上统一。

  • 物理分散:数据存放在通过计算机网络连接的多个节点(site)上,不是堆在一台机器里。
  • 逻辑统一:对用户而言,整个系统仍表现为一个数据库,用户可以像操作单机数据库一样提交查询,无需知道数据存在哪个节点。这种"隐藏位置信息"的能力叫位置透明性(location transparency)。

与集中式的对比

维度 集中式数据库 分布式数据库
数据存放 单节点 多节点分散
逻辑视图 单一 单一(对用户透明)
控制 集中控制 分散,节点局部自治
可用性 单点故障即整体不可用 部分节点故障,其余仍可用
扩展 垂直扩展(换更强主机) 水平扩展(加节点即可)
一致性 本地锁与日志即可 需跨节点协调(如 2PC)

优点与挑战

优点(为什么值得做)

  • 高可用 ⭐:一台机器挂了不等于系统挂了,故障节点可下线修复,其余节点照常服务。
  • 可扩展 ⭐:数据涨了,加一台机器、挪一部分数据过去就行,不必换更贵的大型机。
  • 局部自治:每个节点独立管理自己的数据,业务按地域或部门划分时很自然。

挑战(为什么难)

  • 一致性 ⭐:多个节点各持一份数据,更新时要保证大家看到的一致,需要协调协议,这是分布式最棘手的部分。
  • 网络开销:每次跨节点查询、多节点事务都要在网络上传输数据,网络延迟可能抵消"就近访问"的好处。
  • 复杂度:分片、副本、故障恢复、分布式事务,设计、部署、排错的难度都比集中式高一个量级。

⚠️ 常见错误

  1. 只记"物理分散",漏掉"逻辑统一":没有逻辑统一,用户须自己连对应库,那只是"多台独立数据库连了网",不是分布式数据库。
  2. 以为分布式一定更快:跨节点查询和网络传输有开销,单机瞬间能完成的查询被分散后可能更慢——分布式的收益是可用性与扩展性。
  3. 把"高可用"当成"不出错":高可用指"故障时系统仍能服务",代价是一致性或复杂度。

2.2 体系结构:三层模式映射

一本被拆开的书

把整个数据库想成一本书《学生档案》。全局模式是书的"目录",讲整本书讲什么;分片模式是"怎么切章"——拆成"第一章 个人信息、第二章 成绩";分配模式是"每章放哪个书架"。读者只看到目录,不关心书被拆成几本、放在哪个馆。

三层模式:从"长什么样"到"放哪里"

  1. 全局模式(Global Schema) ⭐:相当于集中式数据库的概念模式,用全局的逻辑结构描述整个分布式数据库。用户看到的就是它。
  2. 分片模式(Fragmentation Schema) ⭐:回答"怎么切"。全局关系被划分为若干逻辑片断(fragment),每个片断仍是一个关系。分片只做逻辑划分,还没决定物理位置。
  3. 分配模式(Allocation Schema) ⭐:回答"放哪里"。把每个片断映射到一个或多个节点(单副本还是多副本),逻辑片断就此落到物理站点。

映射链:全局模式 → 分片模式 → 分配模式 → 物理存储

客户端/服务器模式 与 对等(P2P)模式

  • 客户端/服务器模式(Client/Server):角色不对称。服务器负责存储数据和执行查询,客户端只发请求、展示结果。
  • 对等模式(Peer-to-Peer,P2P):各节点地位平等,既是"客户端"(能发请求)又是"服务器"(能存数据、提供服务),没有中心节点,容错性和扩展性更强。

⚠️ 常见错误

  1. 分不清"分片模式"和"分配模式":分片是"切"、分配是"放",先切后放。
  2. 以为全局模式是真实存储的表:全局模式只是逻辑描述,真实数据切分后分布在各节点。
  3. 把"客户端/服务器"当成"非分布式":C/S 也是分布式的一种形态,与对等模式的区别在于角色是否对称。

2.3 数据分片:怎么把一张大表切开

切西瓜的三种切法

一个大西瓜(一张关系表)怎么分给几桌客人?顺着纹理竖切成瓣,每瓣属性齐全——对应水平分片;只切瓜瓤,每份只含部分属性——对应垂直分片;先竖切再挖瓤——对应混合分片。

四种分片方式

  1. 水平分片(Horizontal Fragmentation) ⭐:按行切,每个片断是原关系满足某条件的一个元组子集。例:学生(学号,姓名,学院) 按学院切——计算机学院的学生软件学院的学生……各片属性列完全相同,只是行数不同。
  2. 垂直分片(Vertical Fragmentation) ⭐:按列切,把属性分成几组。例:学生 切成 (学号,姓名,学院)(学号,成绩)。注意主键(学号)必须留在每个片断里,否则没有公共列,拼不回来。
  3. 导出分片(Derived Fragmentation)跟随别的表切。例:选课 表跟着 学生 表的水平分片走,凡"计算机学院学生"的选课记录放一片。这样"学生 + 他的选课"常在同一个节点,查询不用跨节点。
  4. 混合分片(Hybrid Fragmentation):先水平再垂直(或反之)。例:全校学生先按学院水平切成片,再对"计算机学院片"按列切出"成绩片"。

分片正确性三条规则 ⭐

切完必须能拼回去、不能切丢、不能切重,三条规则是判断标准:

  1. 完备性(Completeness):全局关系的所有数据都必须被分到某个片断,不能遗漏。例:学生表 1000 行,各水平片断行数相加必须恰好等于 1000。
  2. 可重构性(Reconstructability):所有片断能拼回原关系。水平片断用并(UNION)——把各片行拼起来就是原表;垂直片断用连接(JOIN)——按公共主键把各列拼回完整表。
  3. 不相交性(Disjointness):片断之间互不重叠。水平片断要求"同一条记录不出现在两个片断里";垂直片断要求"除主键外,属性列不重复出现",否则列会重复存储。

💡 记忆口诀:完备性——不丢;可重构性——能拼;不相交性——不重

⚠️ 常见错误

  1. 垂直分片忘了保留主键:切成 (姓名,学院)(成绩),没有公共列,用 JOIN 无法重构。
  2. 水平分片的切分条件重叠:如"学院='计算机' 或 学号<1000"与"学号>500"有交集,一条记录落进两片,违反不相交性。
  3. 三条规则只会背名字、说不出操作:完备性对应"数据无遗漏",可重构性对应"水平 UNION、垂直 JOIN",不相交性对应"不重叠"。

2.4 数据分布策略:片断放在哪里

公司档案室的四种摆法

公司有一批文件(片断),档案室有几个(节点),怎么摆?把所有文件塞进一个房间(集中式);按部门一人一个房间各管各的(分割式);每个房间都复印一份全套(全复制式);"常用文件每个房间都有一份,冷门档案只放一个房间"(混合式)。

四种策略与读写开销

  1. 集中式(Centralized):所有片断放在一个节点。场景:数据量小、读写都在一个站点、不需容错的小系统。读/写:本地进行,快——但没有分布式收益,本质是"换个名字的集中式库"。
  2. 分割式(Partitioned):每个片断恰好放一个不同节点,不复制。场景:数据按地域或业务划分,如银行按省存放本地账目。:只涉及本节点片断时快;跨片查询(如统计全国)要把多地数据搬到一处合并,开销大。:本片内快;跨片事务(如转账跨省)需多节点协调,开销大。
  3. 全复制式(Fully Replicated):每个节点都放一份完整副本。场景:读极多、写极少的静态数据,如商品目录、全局配置表。:本地读,最快。:每改一次所有副本都要同步,随节点数线性增长,写频繁时系统被拖垮。
  4. 混合式(Hybrid)部分片断复制、部分片断分割。场景:绝大多数真实系统,如热门商品信息各地有副本、冷门历史订单只放一个节点,兼顾读与写。

💡 记忆口诀读多用复制,写多用分割——复制牺牲写换读,分割牺牲跨片查询换本片读写。

⚠️ 常见错误

  1. 全复制式的读写开销记反:复制越多读越方便、写越累。
  2. 混淆"集中式"与"分割式":集中式所有片断在一点;分割式每个节点各放不同片断。
  3. 选策略只盯着读:给频繁更新的表配全复制,每次写都要全网同步,写性能会灾难性下降。

2.5 CAP 定理 ⭐

一群靠电话同步的朋友

想象你和三个朋友约定"随时同步手头的账目"。某天通信线路断了(网络分区)。这时来了一个新请求,你有两个选择:A——先按本地数据回答(有响应,但可能和朋友不一致);C——拒绝回答,等线路恢复、确认一致了再回应。两个都想做到?不可能——分区期间无法既"立刻回答"又"和朋友完全一致"。这就是 CAP 的核心困境。

三个字母

  • C(Consistency,一致性):所有节点同一时刻看到相同数据,任何读都返回最近一次写入后的值。
  • A(Availability,可用性):每个请求都能在合理时间内得到响应——注意,是"有响应",不承诺数据是最新的。
  • P(Partition Tolerance,分区容错性):即使节点间网络发生分区(通信中断),系统仍能继续运行

三选二,但 P 绕不过

CAP 说分布式系统最多同时满足其中两项。更关键的是——网络分区无法避免(机器会宕、线路会断),所以 P 必须保留,真正的选择只剩 C 和 A:

  • CP(保一致、牺牲可用):例——银行账本。转账时无法确认两个账户余额是否一致,宁可拒绝请求,也绝不返回一笔可能算错的账。
  • AP(保可用、接受短暂不一致):例——缓存、购物车。网络抖动时先返回本地缓存,用户照常下单,稍后后台再同步。
  • CA(无分区时):单机数据库不涉及网络分区,天然是 CA——但它不是分布式。

💡 记忆口诀P 绕不过,C/A 二选一;银行要 C,缓存要 A。

⚠️ 常见错误

  1. 把"三选二"理解成随便挑两个:分布式里 P 无法避免、必须保留,实际只在 C 和 A 之间选——"CA"在联网场景下不存在。
  2. 混淆"可用性"和"一致性":A 保证"有响应",C 保证"响应的是最新且正确的数据"——一个是"有没有",一个是"对不对"。
  3. 以为 CAP 是"三者同时最优":CAP 说的是权衡,不存在既完全一致、又永远可用、还能抗分区的"全能系统"。

2.6 分布式查询处理 ⭐

一张跨分店的订单查询单

总公司要"查全国所有分店中金额超过一万的订单"。你在任意一家分店敲下这条 SQL,流程就像大公司内部协作:总台拆解需求(查询分解)、确认哪个分店有数据(数据定位)、各分店自己优化执行(局部优化)、最后并行干活汇总(全局执行)。

五个步骤(文字推演一个跨节点查询)

全局查询 → 查询分解 → 数据定位 → 局部优化 → 全局执行

学生(学号,姓名,学院,成绩) 按学院水平分片:节点 1 存 计算机学院,节点 2 存 软件学院。用户在节点 1 提交:

查询:SELECT 学号,姓名 FROM 学生 WHERE 学院='计算机' AND 成绩>=90

  1. 全局查询(Global Query):用户在任意节点提交 SQL,看到的是全局逻辑表 学生,无需知道它分了几片、放在哪。
  2. 查询分解(Query Decomposition):把 SQL 改写成等价的关系代数表达式,还不涉及数据位置σ(学院='计算机' ∧ 成绩>=90)(学生),纯粹是"把话翻译成标准算式"。
  3. 数据定位(Data Localization):按分片与分配模式,把 学生 替换成具体片断:σ(学院='计算机' ∧ 成绩>=90)(学生₁ ∪ 学生₂)。此时做片断剪枝(fragment pruning):条件 学院='计算机' 正好命中节点 1 的片断,节点 2 根本不用参与,省掉一次跨节点通信。
  4. 局部优化(Local Optimization):节点 1 拿到自己的那部分表达式,利用本地索引、统计信息选出代价最低的执行计划(如先按 成绩 索引过滤再投影)。
  5. 全局执行(Global Execution):各相关节点并行执行局部计划,结果经网络传回提交节点合并。本例只在节点 1 执行并返回,几乎零跨节点代价。

再看一个必须跨节点的例子:若查询是"所有学院中成绩≥90的学生",两片都有数据,则节点 1、节点 2 并行执行各自的局部查询,结果传回后做并(UNION) 合并再返回。并行是性能来源,合并与传输是网络开销所在。

⚠️ 常见错误

  1. 把"查询分解"和"数据定位"合并成一步:分解把 SQL 译成代数式(不关心数据在哪),定位把代数式映射到具体节点(开始关心数据在哪)。
  2. 忘记用分片条件做剪枝:上例只查计算机学院,若不剪枝,会把节点 2 的软件学院数据也搬过来合并,白白增加网络开销。
  3. 以为"局部优化"发生在全局层面:局部优化是各节点对自己那份表达式独立做,全局层只负责分发、合并。

2.7 分布式事务与两阶段提交(2PC)⭐

一次全员到齐才能交的课程作业

小组作业要求:全组所有人的部分都交齐,这次作业才算数。组长(协调者)逐个问:"你的部分做好了吗?"(阶段一:准备)。若每个人都说"做好了"(全部就绪),组长宣布"交!"(阶段二:提交);只要有一个人说"没做好",组长宣布"全组作废"(阶段二:回滚)。要么全交,要么全不交——这就是分布式事务要保证的"原子性"。

本地事务 vs 分布式事务

  • 本地事务(Local Transaction):只在一个节点上执行,原子性、一致性由该节点自己的日志和锁机制保证,不用和别的节点商量。
  • 分布式事务(Distributed Transaction):一个事务的操作分散在多个节点上执行(如转账:借记在 A 节点、贷记在 B 节点)。单靠各节点本地机制不够,必须由协议协调,保证"要么全提交、要么全回滚"。这个经典协议就是两阶段提交

两阶段提交(2PC)分步推演 ⭐

角色:1 个协调者(Coordinator,事务发起节点)+ n 个参与者(Participants,事务涉及的各节点)。

阶段一:准备(Prepare)

  1. 协调者向所有参与者发送"准备提交(Prepare to commit)"消息。
  2. 每个参与者执行属于自己的写操作(写入本地、记入日志),但不真正提交
  3. 每个参与者投票:可以提交 → 就绪(Ready);出了差错 → 放弃(Abort)

阶段二:提交/回滚(Commit/Abort)

  1. 协调者收集所有投票:
    • 全部"就绪" → 广播"提交(Commit)",各参与者正式提交,事务完成。
    • 任一"放弃" → 广播"回滚(Abort)",各参与者撤销已做操作。
  2. 协调者先把决策写入日志再广播,防止决策后宕机丢记忆。

2PC 的阻塞问题(Blocking Problem) ⭐:2PC 的最大软肋。若协调者在阶段二发出提交消息后、参与者还没收到前宕机,参与者无法单方面决定提交还是回滚,只能一直等待恢复,事务被挂起——这就是阻塞。改进方案是三阶段提交(3PC),在阶段一、二之间加"预提交(Pre-commit)"缓冲,缩小阻塞窗口,但协议更复杂。

⚠️ 常见错误

  1. 以为"有一个参与者就绪就能提交":2PC 要求所有参与者都回"就绪"才提交,任一放弃就全体回滚——"全部"和"任一"最容易记反。
  2. 把"准备"阶段当成"已经提交":阶段一只写日志、做准备,数据还没真正提交;提交发生在阶段二收到提交消息之后。
  3. 以为 2PC 解决了分布式事务的所有问题:它解决了原子性,但没解决阻塞——协调者故障时参与者会被挂起,只能等待恢复。

🧠 记忆口诀

  1. 分布式定义:物理分散,逻辑统一。
  2. 三层模式:全局模式(长什么样)→ 分片模式(怎么切)→ 分配模式(放哪里)。
  3. 分片正确性:完备不丢、可重构能拼、不相交不重
  4. 分布策略:集、割、复、混;读多用复制,写多用分割
  5. CAPP 绕不过,C/A 二选一;银行要 C,缓存要 A
  6. 查询五步:全局查询 → 查询分解 → 数据定位 → 局部优化 → 全局执行。
  7. 2PC:先准备,再表决;全就绪才提交,一反对就回滚

⭐ 考点清单

  1. 分布式数据库的定义:"物理分散、逻辑统一"。
  2. 与集中式对比:优点(高可用、可扩展、局部自治)与挑战(一致性、网络开销、复杂度)。
  3. 三层模式映射:全局→分片→分配;客户端/服务器与对等(P2P)模式的区别。
  4. 水平分片(按行)、垂直分片(按列,留主键)、导出分片(跟随别的表)、混合分片。
  5. 分片正确性三规则:完备性、可重构性(水平 UNION、垂直 JOIN)、不相交性。
  6. 四种分布策略的读写开销:集中式、分割式、全复制式(读快写慢)、混合式。
  7. CAP:C / A / P 含义;P 不可绕;银行(CP)与缓存(AP)的权衡。
  8. 分布式查询五步流程与"片断剪枝";2PC 两阶段、阻塞问题;分布式与本地事务的区别。

📌 中英术语表

中文 English
分布式数据库 distributed database
分布式数据库管理系统 DDBMS
位置透明性 location transparency
全局模式 global schema
分片模式 fragmentation schema
分配模式 allocation schema
水平分片 horizontal fragmentation
垂直分片 vertical fragmentation
导出分片 derived fragmentation
混合分片 hybrid fragmentation
完备性 completeness
可重构性 reconstructability
不相交性 disjointness
集中式 / 分割式 centralized / partitioned
全复制式 / 混合式 fully replicated / hybrid
一致性 consistency
可用性 availability
分区容错性 partition tolerance
查询分解 query decomposition
数据定位 data localization
局部优化 local optimization
全局执行 global execution
片断剪枝 fragment pruning
分布式事务 distributed transaction
本地事务 local transaction
两阶段提交 two-phase commit (2PC)
协调者 / 参与者 coordinator / participant
阻塞问题 blocking problem
三阶段提交 three-phase commit (3PC)