ER 建模与关系基数
将需求转换为实体、关系和连接表。
ER 建模与关系基数 是 CoddyKit 上的免费 SQL Interview Prep 课时。 这是第 2 节课,共 4 节。 你可以在下方免费阅读本课时的完整内容 — 然后在浏览器中使用内置代码编辑器和全天候 AI 导师进行实践。 这是 SQL Interview Prep 学习路径的一部分,你的进度在网页和 CoddyKit 应用中同步。 SQL Interview Prep 课程共包含 4 节课。
为什么 ER 建模会出现在面试中
在规范化之后,面试官会检验您是否能将需求转化为模式。问题通常是开放式的:"请为一个网约车应用设计数据库"或"请为一个图书馆系统建模。"
这是一项实体-关系(ER)建模练习。面试官会观察您如何识别实体、属性以及实体之间的关系,包括基数。
这项技能要求您把英语中的名词和动词转换成表和外键。
实体、属性和关系
每个 ER 模型都由三个基本构件组成:
- 实体:您要存储其数据的事物(客户、订单、产品)。通常会成为一张表。
- 属性:实体的一个特征(名称、价格、创建时间)。通常会成为一列。
- 关系:实体之间的连接方式(客户下达订单)。通过外键或连接表实现。
根据题目提示:名词变成实体或属性,动词变成关系。
基数:核心概念
基数描述一个实体的多少个实例与另一个实体相关联。主要有三类:
- 一对一(1:1):这里的一行最多对应那边的一行。
- 一对多(1:N):这里的一行对应那边的多行(最常见)。
- 多对多(M:N):两边的多行都可以对应另一边的多行。
正确确定基数后,才能决定外键放在哪里,以及是否需要连接表。
实现一对多关系
一对多关系通过将外键放在“多”这一侧来实现。一个客户拥有多个订单,因此每个订单行都携带customer_id。
面试时,请始终明确说明方向:"一个客户对应多个订单,因此 FK 位于订单表中。"
CREATE TABLE customers (
customer_id INT PRIMARY KEY,
name VARCHAR(100)
);
CREATE TABLE orders (
order_id INT PRIMARY KEY,
customer_id INT NOT NULL,
order_date DATE,
FOREIGN KEY (customer_id) REFERENCES customers(customer_id)
);实现多对多关系
关系型数据库无法直接存储 M:N 关系。面试官希望听到的答案是使用连接表(也称为桥接表、链接表或关联表)。
学生可以选修多门课程;每门课程也有许多学生。创建一张enrollments表,让它的键由两个外键组合而成。这样就能将 M:N 关系拆解为两个 1:N 关系。
CREATE TABLE students (
student_id INT PRIMARY KEY,
name VARCHAR(100)
);
CREATE TABLE courses (
course_id INT PRIMARY KEY,
title VARCHAR(100)
);
CREATE TABLE enrollments (
student_id INT,
course_id INT,
enrolled_at DATE,
PRIMARY KEY (student_id, course_id),
FOREIGN KEY (student_id) REFERENCES students(student_id),
FOREIGN KEY (course_id) REFERENCES courses(course_id)
);连接表可以存储数据
一个常见的后续问题是:"学生在一门课程中取得的成绩应该存储在哪里?"
成绩属于关系,而不是单独属于学生或课程。因此,成绩应该放在连接表中。这正是面试官要考察的理解:M:N 关系的属性应存储在桥接表上。
例如:选课日期、成绩、订单明细中的数量,以及项目成员关系中的角色。
ALTER TABLE enrollments
ADD COLUMN grade CHAR(2);
-- grade describes THIS student in THIS course,
-- so it belongs on the junction table实现一对一关系
1:1 关系比较少见。实现方式是:为从属表提供一个同时也是唯一键的外键(通常它本身就是主键)。
例如,user和user_profile分别表示用户及其扩展的可选信息。将user_id设为资料表的主键,就能保证每个用户最多拥有一份资料。
CREATE TABLE users (
user_id INT PRIMARY KEY,
email VARCHAR(255)
);
CREATE TABLE user_profiles (
user_id INT PRIMARY KEY, -- 1:1 enforced here
bio TEXT,
avatar_url VARCHAR(255),
FOREIGN KEY (user_id) REFERENCES users(user_id)
);可选性和参与性
基数还有面试官很关注的第二个维度:可选性(也称为参与性)。
- 必需:每个订单都必须有一个客户,因此
customer_id是NOT NULL。 - 可选:用户可能有资料,也可能没有,因此这种关系可以不存在。
您可以在外键上使用NOT NULL来表达必需的参与性。提到对 NULL 的可接受性,说明您考虑了真实约束,而不只是表的结构。
自引用关系
有些关系会让一个实体指向自身。例如,员工拥有一名同为员工的经理;类别拥有一个父类别。
您可以使用引用同一张表的外键来建模这种关系。面试官希望您能将其应用于组织架构图和树形结构,它也天然适合与自连接和递归公用表表达式结合使用。
CREATE TABLE employees (
employee_id INT PRIMARY KEY,
name VARCHAR(100),
manager_id INT NULL,
FOREIGN KEY (manager_id) REFERENCES employees(employee_id)
);
-- manager_id NULL = top of the hierarchy (e.g. CEO)小型建模演练
练习使用从动词到关系的方法。题目:"客户下达订单;每个订单包含多个产品;产品属于供应商。"
- 客户 1:N 订单(FK 位于订单表的客户标识列中)。
- 订单 M:N 产品 -> 连接表
order_items(包含数量)。 - 供应商 1:N 产品(FK 位于产品表的供应商标识列中)。
说明每个基数,并指出键放在哪里。这种讲解方式就是面试中取得成功的关键。
需要提出的澄清问题
面试官会认可那些在设计之前先提问的候选人。好的澄清问题包括:
- "一个产品可以属于多个供应商吗?"(决定是一对多还是多对多)。
- "每个订单都必须至少包含一项明细吗?"(参与性)。
- "我们需要历史记录,还是只需要当前状态?"(决定是否需要额外的表)。
这些答案会改变基数和表的数量,因此绝不要想当然。主动提问体现了您的资历。
快速检查
您正在为学生和课程建模,其中每个学生可以选修多门课程,每门课程也有许多学生。
回顾:ER 建模与基数
现在,您已经能够处理开放式的模式设计问题:
- 将 名词转换为实体和属性,将动词转换为关系。
- 1:N:将外键放在多的一方。
- M:N:使用同时保存两个外键以及任何关系属性的连接表。
- 1:1:在依赖表中使用共享键或唯一键。
- 使用
NOT NULL表示必须参与,并使用自引用外键表示层次结构。 - 在确定基数之前,先提出澄清问题。
常见问题解答
「ER 建模与关系基数」课时是免费的吗?
是的 — 「ER 建模与关系基数」的完整文本可在网页上免费阅读。要进行交互式练习(内置代码编辑器和全天候 AI 导师)并解锁 SQL Interview Prep 课程的其余内容,请升级到 CoddyKit PRO。 SQL Interview Prep 课程共包含 4 节课。
「ER 建模与关系基数」这节课中我会学到什么?
将需求转换为实体、关系和连接表。 你通过在浏览器中直接运行的动手代码来练习 SQL Interview Prep,全天候 AI 导师会在你学习这节课的过程中回答你的问题。
学习 SQL Interview Prep 需要有经验吗?
无需任何先前经验。CoddyKit 上的 SQL Interview Prep 课程适合初学者到高级学习者,你可以从这里开始或从头开始,按照自己的节奏学习。 这是第 2 节课,共 4 节。
「ER 建模与关系基数」课时需要多长时间?
大多数 CoddyKit 课程大约需要 5–10 分钟。每节课都很精短且互动,所以你能稳步进步,并在网页和应用中从离开的地方继续。
我能在这节 SQL Interview Prep 课中编写并运行代码吗?
能。每节 SQL Interview Prep 课都包含内置代码编辑器,你可以在浏览器中直接编写并运行真实代码,并获得即时 AI 反馈 — 无需本地设置。
此课程中的所有课时
- 通过第三范式实现规范化
- ER 建模与关系基数
- 星型模式与数据仓库设计
- 完整模拟面试题集