外键和主键概念题
Foreign and Primary Key Conceptual Questions
我是SQL/PostgreSQL的新手,我有一个关于外键和一般键的概念性问题:
假设我有两个表:Table A
和 Table B
.
A
有一堆列,其中两个是 A.id, A.seq
。主键是 btree(A.id, A.seq)
,它有一个 A.id
引用 B.id
的外键约束。请注意,A.seq
是一个顺序列(第一行的值为 1,第二行的值为 2,依此类推)。
现在说B
有一堆列,其中一个就是上面提到的B.id
。主键是 btree(B.id)
.
我有以下问题:
btree
到底是做什么的?在 btree 中有两个列名而不是只有一个(如 btree(B.id)
)有什么意义。
- 为什么
A
引用 B
而不是 B
引用 A
很重要?为什么外键的顺序很重要??
非常感谢!如果我对任何内容使用了不正确的术语,请纠正我。
编辑:我正在使用 postgres
你的数据结构没有意义。为什么A的主键会同时有id
和name
?通常它只是 id
。在某些数据模型中,您可能添加了版本或时间戳。我想不出一个合理的数据模型,其中还包括 name
。
此外,B
的外键必须同时指向 id
和 name
。
但是,您的问题是 btree
的用途是什么?大多数数据库没有这样的选项。主键通常表示为:
id int primary key;
constraint unq_t_id primary key (id);
btree
是一种索引——实际上是我所知道的所有数据库中的默认索引类型。具有大量可用索引类型的数据库(例如 Postgres),您可以指定与主键关联的索引类型。
针对您的问题:
有几种实现唯一键的策略。最常见的一种是使用使用“b-tree”策略的“唯一”索引。这就是“btree”在 PostgreSQL 中的意思。
在一个键中有两列仅取决于您要如何设计 table。当您拥有一个包含多个列的键时,称为“复合键”。
当 A
引用 B
时,B
中的列必须代表一个“键”。 A
中的列不代表一个键,而只是一个 reference。实际上,该列的 A
中的值可以重复;也就是说,A
中的多行可以 指向 到 B
.
中的同一行
btree 索引按排序顺序存储值,这意味着您不仅可以搜索单个主键值,还可以高效地搜索一系列值:
SELECT ... WHERE id between 6060842 AND 8675309
PostgreSQL还支持其他index types, but only btree is supported for a unique index(例如主键)。
在您的 B
table 中,主键是单列 id
意味着 id
中的每个值只能存在一行。换句话说,它是唯一的,如果你通过主键搜索一个值,它最多只能找到一行(如果你没有该值的行,它也可能会找到零行)。
您的 A
table 中的主键用于 (id, seq)
。这意味着 id
的每个值可以有多个行。 seq
的每个值也可以有多行,只要它们用于不同的 id
值。但是,该组合必须是唯一的。同一对值不能超过一行。
当 A
中的外键引用 B
时,这意味着该行必须存在于 B
中,然后才能将行存储在 A
中相同的 id
值。但是反过来就没有必要了。
示例:
假设 B
是给用户的,A
是给 phone 的。您必须先存储用户,然后才能存储该用户的 phone 记录。您可以为该用户存储一个或多个 phone,在 A
table 中每行一个。我们说 A
中的一行引用了 B
中的用户行,意思是“这个 phone 属于用户#1234。”
但反向不受限制。用户可能没有 phone(至少不为该数据库所知),因此不需要 B
引用 A
。换句话说,用户不需要 phone。您可以在 B
(用户)中存储一行,即使在 A
(phones)中没有该用户的行。
引用还意味着如果另一个 table 中的行引用 B
中的给定行,则您不能 DELETE FROM B WHERE id = ?
。删除该用户会导致其他行成为孤立行。如果他们引用的用户行被删除,没有人能够知道这些 phone 属于谁。
我是SQL/PostgreSQL的新手,我有一个关于外键和一般键的概念性问题:
假设我有两个表:Table A
和 Table B
.
A
有一堆列,其中两个是 A.id, A.seq
。主键是 btree(A.id, A.seq)
,它有一个 A.id
引用 B.id
的外键约束。请注意,A.seq
是一个顺序列(第一行的值为 1,第二行的值为 2,依此类推)。
现在说B
有一堆列,其中一个就是上面提到的B.id
。主键是 btree(B.id)
.
我有以下问题:
btree
到底是做什么的?在 btree 中有两个列名而不是只有一个(如btree(B.id)
)有什么意义。- 为什么
A
引用B
而不是B
引用A
很重要?为什么外键的顺序很重要??
非常感谢!如果我对任何内容使用了不正确的术语,请纠正我。
编辑:我正在使用 postgres
你的数据结构没有意义。为什么A的主键会同时有id
和name
?通常它只是 id
。在某些数据模型中,您可能添加了版本或时间戳。我想不出一个合理的数据模型,其中还包括 name
。
此外,B
的外键必须同时指向 id
和 name
。
但是,您的问题是 btree
的用途是什么?大多数数据库没有这样的选项。主键通常表示为:
id int primary key;
constraint unq_t_id primary key (id);
btree
是一种索引——实际上是我所知道的所有数据库中的默认索引类型。具有大量可用索引类型的数据库(例如 Postgres),您可以指定与主键关联的索引类型。
针对您的问题:
有几种实现唯一键的策略。最常见的一种是使用使用“b-tree”策略的“唯一”索引。这就是“btree”在 PostgreSQL 中的意思。
在一个键中有两列仅取决于您要如何设计 table。当您拥有一个包含多个列的键时,称为“复合键”。
当
中的同一行A
引用B
时,B
中的列必须代表一个“键”。A
中的列不代表一个键,而只是一个 reference。实际上,该列的A
中的值可以重复;也就是说,A
中的多行可以 指向 到B
.
btree 索引按排序顺序存储值,这意味着您不仅可以搜索单个主键值,还可以高效地搜索一系列值:
SELECT ... WHERE id between 6060842 AND 8675309
PostgreSQL还支持其他index types, but only btree is supported for a unique index(例如主键)。
在您的 B
table 中,主键是单列 id
意味着 id
中的每个值只能存在一行。换句话说,它是唯一的,如果你通过主键搜索一个值,它最多只能找到一行(如果你没有该值的行,它也可能会找到零行)。
您的 A
table 中的主键用于 (id, seq)
。这意味着 id
的每个值可以有多个行。 seq
的每个值也可以有多行,只要它们用于不同的 id
值。但是,该组合必须是唯一的。同一对值不能超过一行。
当 A
中的外键引用 B
时,这意味着该行必须存在于 B
中,然后才能将行存储在 A
中相同的 id
值。但是反过来就没有必要了。
示例:
假设 B
是给用户的,A
是给 phone 的。您必须先存储用户,然后才能存储该用户的 phone 记录。您可以为该用户存储一个或多个 phone,在 A
table 中每行一个。我们说 A
中的一行引用了 B
中的用户行,意思是“这个 phone 属于用户#1234。”
但反向不受限制。用户可能没有 phone(至少不为该数据库所知),因此不需要 B
引用 A
。换句话说,用户不需要 phone。您可以在 B
(用户)中存储一行,即使在 A
(phones)中没有该用户的行。
引用还意味着如果另一个 table 中的行引用 B
中的给定行,则您不能 DELETE FROM B WHERE id = ?
。删除该用户会导致其他行成为孤立行。如果他们引用的用户行被删除,没有人能够知道这些 phone 属于谁。