Backend-Development
  • Introduce
  • 操作系统和Linux
    • 操作系统基础
      • 进程
      • 进程间通信
      • 线程 & 协程
      • 调度
      • 互斥 & 同步
      • 死锁 & 饥饿
      • 内存管理
      • 文件系统
      • IO
    • Linux
      • Linux共享内存
      • Linux进程的内存空间布局
      • 僵尸进程和孤儿进程
      • 用户态和内核态
      • Linux进程调度算法
      • 理解inode
      • Linux进程间通信
      • Linux虚拟文件系统
      • CPU亲和性
      • 零拷贝技术
      • Linux IO栈
    • Linux常考命令
      • 管道和重定向
      • 文本处理三剑客
      • 文件和目录管理
      • 进程&内存&CPU管理
      • 用户&组管理
      • 网络管理
    • Linux系统调用
      • 内存
      • 进程
    • Linux系统编程
      • Linux堆内存管理
      • pthread库
    • Shell编程
  • 网络通信与网络编程
    • 计算机网络
      • 应用层其他协议
      • 应用层之DNS协议
      • 应用层之HTTP/3协议
      • 应用层之HTTPS协议
      • 应用层之HTTP协议
      • 传输层之UDP协议
      • 传输层之TCP协议
      • 网络层其他协议
      • 网络层之IP协议
      • 数据链路层
      • 物理层
    • 网络编程
      • cookie、session、token
      • TCP的粘包问题
      • 幂等性
      • 网络IO模型
      • 多路复用IO
      • Socket编程
      • 高并发服务器
    • Linux网络编程之底层
      • 传输控制块TCB
      • TCP数据发送之tcp_sendmsg()
      • TCP选项之MSS
    • 网络安全
    • Nginx
    • Wireshark
    • Libevent
  • 数据库
    • 数据库相关概念
    • 关系数据库设计范式
    • SQL
      • 初级SQL
      • 中级SQL
      • 高级SQL
    • Redis
      • Redis数据结构
      • Redis数据类型
      • 数据持久化
      • 雪崩 & 击穿 & 穿透
      • 主从复制
      • Redis集群
    • MySQL
      • MySQL数据类型
      • 事务
      • 事务隔离
      • 存储引擎
      • MyISAM与InnoDB
      • 锁机制
      • 索引
      • 联合索引
      • 主从复制
      • MySQL集群
      • MySQL使用总结
    • MongoDB
      • 启动与停止
      • 查询
    • Memcached
  • 组成原理和体系结构
    • 定点数 & 浮点数 & 内存
    • 体系结构
  • 编译和调试
    • 编译原理
    • Gdb调试
    • 内存屏障
    • 编译器优化
    • make/Makefile
    • cmake
    • 交叉编译
    • C++单元测试
    • 单元测试之Google Test
  • 设计模式
    • 设计模式
    • “组件协作”模式
  • 其他
    • 正则表达式
      • 基本正则表达式
      • 扩展正则表达式
    • Git版本控制
      • 提交代码
      • 常用命令
    • 编码和字符集
    • Vim用法
    • 一文解“锁”
    • 无锁技术
    • 面试中的“锁”
  • 面试题
    • 计算机网络面试题
    • 操作系统面试题
    • 数据库面试题
    • 其他面试题
    • 场景题总结
    • 智力题
Powered by GitBook
On this page
  • 1、第一范式(确保每列保持原子性)
  • 2、第二范式(确保表中的每列都和主键相关)
  • 3、第三范式(确保每列都和主键列直接相关,而不是间接相关)
  • 4、巴斯-科德范式(BCNF)
  • 5、第四范式

Was this helpful?

  1. 数据库

关系数据库设计范式

Previous数据库相关概念NextSQL

Last updated 4 years ago

Was this helpful?

为了建立冗余较小、结构合理的数据库,设计数据库时必须遵循一定的规则。在关系型数据库中这种规则就称为范式(normal form)。范式是符合某一种设计要求的总结。要想设计一个结构合理的关系型数据库,必须满足一定的范式。越高的范式数据库冗余越小。

目前关系数据库有六种范式

  • 第一范式(1NF)

  • 第二范式(2NF)

  • 第三范式(3NF)

  • 巴斯-科德范式(BCNF)

  • 第四范式(4NF)

  • 第五范式(5NF,又称完美范式)

1、第一范式(确保每列保持原子性)

第一范式是最基本的范式。如果数据库表中的所有字段值都是不可分解的原子值,就说明该数据库表满足了第一范式。

第一范式的合理遵循需要根据系统的实际需求来定。比如某些数据库系统中需要用到“地址”这个属性,本来直接将“地址”属性设计成一个数据库表的字段就行。但是如果系统经常会访问“地址”属性中的“城市”部分,那么就非要将“地址”这个属性重新拆分为省份、城市、详细地址等多个部分进行存储,这样在对地址中某一部分操作的时候将非常方便。这样设计才算满足了数据库的第一范式,如下表所示:

在任何一个关系数据库中,第一范式(1NF)是对关系模式的设计基本要求,一般设计中都必须满足第一范式(1NF)。不过有些关系模型中突破了1NF的限制,这种称为非1NF的关系模型。换句话说,是否必须满足1NF的最低要求,主要依赖于所使用的关系模型。

第二范式在第一范式的基础之上更进一层。第二范式(2NF)要求实体的属性完全依赖于主关键字。所谓完全依赖是指不能存在仅依赖主关键字一部分的属性(主要针对联合主键而言),如果存在,那么这个属性和主关键字的这一部分应该分离出来形成一个新的实体,新实体与原实体之间是一对多的关系。为实现区分通常需要为表加上一个列,以存储各个实例的唯一标识。也就是说在一个数据库表中,一个表中只能保存一种数据,不可以把多种数据保存在同一张数据库表中。简而言之,第二范式就是在第一范式的基础上属性完全依赖于主键。

比如要设计一个订单信息表,因为订单中可能会有多种商品,所以要将订单编号和商品编号作为数据库表的联合主键,如下表所示:

订单信息表

这样就产生一个问题:这个表中是以订单编号和商品编号作为联合主键。这样在该表中商品名称、单位、商品价格等信息不与该表的主键相关,而仅仅是与商品编号相关。所以在这里违反了第二范式的设计原则。而如果把这个订单信息表进行拆分,把商品信息分离到另一个表中,把订单项目表也分离到另一个表中,就可以了。如下所示:

这样设计,在很大程度上减小了数据库的冗余。如果要获取订单的商品信息,使用商品编号到商品信息表中查询即可。

第三范式需要确保数据表中的每一列数据都和主键直接相关,而不能间接相关。 简而言之,第三范式就是属性不依赖于其它非主属性,也就是在满足2NF的基础上,任何非主属性不得传递依赖于主属性。

比如在设计一个订单数据表的时候,可以将客户编号作为一个外键和订单表建立相应的关系。而不可以在订单表中添加关于客户其它信息(比如姓名、所属公司等)的字段。如下面这两个表所示的设计就是一个满足第三范式的数据库表。

这样在查询订单信息的时候,就可以使用客户编号来引用客户信息表中的记录,也不必在订单信息表中多次输入客户信息的内容,减小了数据冗余。

Boyce-Codd Normal Form(巴斯-科德范式):在 3NF 的基础上,没有任何属性完全函数依赖于非候选码的任何一组属性(消除主属性对于码的部分函数依赖和传递依赖)。

3NF 不允许非主属性被另一个非主属性决定,但允许主属性被非主属性决定,而 BCNF 中,任何属性(包括非主属性和主属性)都不能被非主属性所决定。

在 BCNF 的基础上,消除表中的多值依赖

“多值依赖”的定义为:设 R(U)R(U)R(U) 是属性集 UUU 上的一个关系模式。 XXX , YYY , ZZZ 是 UUU 的子集,并且 Z=U−X−YZ=U-X-YZ=U−X−Y 。关系模式 R(U)R(U)R(U) 中多值依赖 X→→YX\rightarrow\rightarrow YX→→Y 成立,当且仅当对 R(U)R(U)R(U) 的任一关系 rrr ,给定的一对 (x,z)(x, z)(x,z) 值有一组 YYY 的值,这组值仅仅决定于 xxx 值而与 zzz 值无关。

例如:“商店”表中,有三个键属性:name(商店名称),type(商品供应类型),location(所在地区),满足 BCNF 范式,假设每个商店在任意地区都提供同等数量的供应类型,那么 name(不是超键)存在非平凡多值依赖:

name →→ type
name →→ location

即同一个商店,存在 type 与 location 的冗余。不满足 4NF。

2、第二范式(确保表中的每列都和主键相关)

3、第三范式(确保每列都和主键列直接相关,而不是间接相关)

4、巴斯-科德范式(BCNF)

5、第四范式

✏️
✏️
✏️
✏️
✏️