SQL的关系模型
主键
选取主键的一个基本原则是:不使用任何业务相关的字段作为主键
因此,身份证号、手机号、邮箱地址这些看上去可以唯一的字段,均不可用作主键。
作为主键最好是完全业务无关的字段,我们一般把这个字段命名为id
。
常见的可作为id
字段的类型有:
- 自增整数类型:数据库会在插入数据时自动为每一条记录分配一个自增整数,这样我们就完全不用担心主键重复,也不用自己预先生成主键;
- 全局唯一GUID类型:使用一种全局唯一的字符串作为主键,类似
8f55d96b-8acc-4636-8cb8-76bf8abc2f57
。GUID算法通过网卡MAC地址、时间戳和随机数保证任意计算机在任意时间生成的字符串都是不同的,大部分编程语言都内置了GUID算法,可以自己预算出主键。
如果使用INT自增类型,那么当一张表的记录数超过2147483647(约21亿)时,
会达到上限而出错。使用BIGINT自增类型则可以最多约922亿亿条记录。
联合主键
关系数据库实际上还允许通过多个字段唯一标识记录,即两个或更多的字段都设置为主键,这种主键被称为联合主键
对于联合主键,允许一列有重复,只要不是所有主键列都重复即可
没有必要的情况下,我们尽量不使用联合主键,因为它给关系表带来了复杂度的上升
外键
可以把数据与另一张表关联起来,这种列称为外键
通过定义外键约束,关系数据库可以保证无法插入无效的数据。即如果
classes
表不存在id=99
的记录,students
表就无法插入class_id=99
的记录。
由于外键约束会降低数据库的性能,大部分互联网应用程序为了追求速度,并不设置外键约束,而是仅靠应用程序自身来保证逻辑的正确性
要删除一个外键约束,也是通过ALTER TABLE
实现的:
ALTER TABLE studentsDROP FOREIGN KEY fk_class_id;
注意:删除外键约束并没有删除外键这一列。删除列是通过DROP COLUMN …
实现的
还有一些应用会把一个大表拆成两个一对一的表,目的是把经常读取和不经常读取的字段分开,以获得更高的性能。例如,把一个大的用户表分拆为用户基本信息表
user_info
和用户详细信息表user_profiles
,大部分时候,只需要查询user_info
表,并不需要查询user_profiles
表,这样就提高了查询速度
索引
在关系数据库中,如果有上万甚至上亿条记录,在查找记录的时候,想要获得非常快的速度,就需要使用索引
索引是关系数据库中对某一列或多个列的值进行预排序的数据结构。
通过使用索引,可以让数据库系统不必扫描整个表,
而是直接定位到符合条件的记录,这样就大大加快了查询速度。
索引的效率取决于索引列的值是否散列,即该列的值如果越互不相同,那么索引效率越高。
反过来,如果记录的列存在大量相同的值,例如gender列,大约一半的记录值是M,另一半是F,因此,对该列创建索引就没有意义。
可以对一张表创建多个索引。索引的优点是提高了查询效率,
缺点是在插入、更新和删除记录时,需要同时修改索引,
因此,索引越多,插入、更新和删除记录的速度就越慢。
对于主键,关系数据库会自动对其创建主键索引。使用主键索引的效率是最高的,因为主键会保证绝对唯一。