社区
MS-SQL Server
帖子详情
主键设计,想看看大家的做法?
永生天地
2010-10-20 02:35:30
最早工作时,我们的项目中主键基本都是和业务关系很紧密的,一般都是业务上用到的code,因此有很多复合主键。
后期不知道是哪个大仙来了,提出来要用无意义的自增,又或者是guid之类的,与业务无关,因此所有表就一个主键。
后来换了工作(外包的),发现他们用mysql,主键是根据业务需要编出来的code,又会出来很多复合主键。
大家都用数据库,我很想知道更多的项目是如何来考虑主键的设计的?
好久不来了,散一下分吧。
...全文
606
53
打赏
收藏
主键设计,想看看大家的做法?
最早工作时,我们的项目中主键基本都是和业务关系很紧密的,一般都是业务上用到的code,因此有很多复合主键。 后期不知道是哪个大仙来了,提出来要用无意义的自增,又或者是guid之类的,与业务无关,因此所有表就一个主键。 后来换了工作(外包的),发现他们用mysql,主键是根据业务需要编出来的code,又会出来很多复合主键。 大家都用数据库,我很想知道更多的项目是如何来考虑主键的设计的? 好久不来了,散一下分吧。
复制链接
扫一扫
分享
转发到动态
举报
写回复
配置赞助广告
用AI写文章
53 条
回复
切换为时间正序
请发表友善的回复…
发表回复
打赏红包
jyh070207
2012-01-31
打赏
举报
回复
根据需求来,如有唯一编号或单号的,就以唯一的编号或单号做为主键,没有的话就用自增的id(identity),
一般主从表结构中, 主表的编号或单号为主键,从表以id为主键,在从表的单号上建索引
唐诗三百首
2012-01-31
打赏
举报
回复
2010年的帖了,楼主还是结了吧.
shengr617
2012-01-31
打赏
举报
回复
我觉得还是根据业务需求,怎么好就怎么设。向各位高人学习中。
SQLCenter
2010-10-21
打赏
举报
回复
这个问题,看看例子数据库里面是怎么做的,就一目了然了。
claro
2010-10-21
打赏
举报
回复
1、不可教条。
2、选合适的。
3、选简便的。
jiao3630
2010-10-21
打赏
举报
回复
identity, newid()只要能标识唯一 怎么方便怎么来
obuntu
2010-10-21
打赏
举报
回复
其实就一句话,看情况而定。
另外,不建议使用guid,第一是空间大,第二是无序性。
Passage2011
2010-10-21
打赏
举报
回复
[Quote=引用 17 楼 fredrickhu 的回复:]
surrogate key,指添加的无意义的列来作为主键,一般是用identity列。
这个用得比较多 简单名了 也是唯一的
不过涉及到一个问题
identity列一旦删除了会导致缺号 这样有什么会有一定的麻烦
[/Quote]
删除用一个字段标记,不是delete
feilniu
2010-10-21
打赏
举报
回复
参考资源:
1. 《SQL编程风格》(ISBN:978-7-115-18582-2)一书3.13节和第五章的论述。
2.
http://en.wikipedia.org/wiki/Natural_key
3.
http://en.wikipedia.org/wiki/Surrogate_key
feilniu
2010-10-21
打赏
举报
回复
个人的一点想法:
自然键(Natural Key)和替代键(Surrogate Key)的争论是执迷于表相,偏离了数据库设计的本质。
在数据库设计中,
一个表是一类事物(物件object和事实fact的统称)的集合,表的字段是用来描述各类事物的概念;表的每行记录表示一个该类事物,该记录在各个字段的值描述了该事物的特征(即特征向量),主键是一个特殊的字段——它是该事物的唯一标识。
所以,
一个好的数据库设计,要保证系统中的每个表(事物)和字段(概念)都是有意义的
。只有这样,才能最大限度保持业务系统在逻辑上与现实业务的对应,才能降低开发、维护、运营人员的理解成本。
KISS原则
。
主键字段特殊之处在于:1. 主键常常需要作为其它表的外键被引用;2. 主键通常会被定义为聚集索引。这两点使得主键的字段数量和空间大小成为影响开发效率和运行性能的很重要的问题。
因此,对于自然的、在现实世界有意义的编码,如日期、邮编、社会保险号等,(通常是社会约定俗成,或由权威机构定义),往往可以采用自然键。对于在现实世界没有直接意义、需要自己定义的编码,如用户编号、订单号、产品编码、等,则需要自己用系统生成,这种情况被称为替代键。
常用的替代键的生成方式:1. 预定义,即按一定规则编制,如学校的学号可能是“学生类型+入学年份+学院专业+班级+班级内编号”、员工号可能是“E000001”这样的前辍+编码的形式。2. 纯自动生成,如GUID或自增序列,这种是比较偷懒的方式。
尽管替代键不是自然原本就有的,但经过定义和生成之后,每个替代键作为一个系统内的概念和事物的标识,就具有了业务意义。比如系统的订单号可能仅仅是自增类型的一个3000001,但经过定义之后,这就表示一个订单,这就是有意义的。
换言之,
选择主键的标准,不在于它的生成方式是自然键还是替代键,而在于经过定义之后它要保证在业务系统中有意义,同时尽量满足唯一、稳定、熟悉性、可验证、简单、空间小的要求。
举例说明:
比如对于一个SNS网站系统:
用户表示一个网站的使用者,通常是内部生成UserID,一个UserID可以绑定一个或多个(看系统设计需求)Email地址或OpenID(Google/Yahoo等提供的验证服务)。这个内部UserID可能是GUID或自增整数,但一个UserID就严格地表示一个网站用户。(争论它是自然键还是替代键有意义吗?)
假如这个SNS网站是关于读书的,那么网站系统需要有书这样事物,是采用ISBN还是自定义BookID,通常后者比较好。通过自增整数生成BookID,但同时需要用唯一约束限定一个BookID只能有一个ISBN10或ISBN13。
对于用户收藏书这件事情,用户与书是多对多关系,定义用户收藏表UserFavorite(#UserID,#BookID,CollectTime),但一个用户对一本书只有收藏或未收藏两种状态,所以用(UserID,BookID)作为复合主键是自然的选择。用户收藏表通常不是被其它表引用,其主键不需要作为其它表的外键,因此如果在这个表里添加一个自增主键ID,没有任何意义,而且还需要在(UserID,BookID)上添加唯一约束。浪费一个ID的4个字节,浪费一个额外索引的空间,更重要的,多增加一个无意义ID,还浪费更宝贵的资源——开发人员的注意和精力。
jxcyz228
2010-10-21
打赏
举报
回复
[Quote=引用 15 楼 billpu 的回复:]
补充一下,我9楼说的那个员工信息表的问题
因为业务情况的不可测,造成对有意义主键的失控
前一阵单位里有一个员工离职了,员工号当然作废的.过了半年之后,让我吃惊的是这个员工又回来了.这下好了,人事来找我商量说想给这个员工原来的工号,但是录入系统提示这个员工号已经存在.(因为我把员工号当作主键标识,员工临时只是加了字段tag,并没有真正删除记录).说出问题了.
然后就和人事进行了激烈的辩论,这种……
[/Quote]
不说主键的事。就说这个员工号,我一般是设计一个“是否离职”字段。因为员工号在下游很多表中都会有。所以一般不允许删除。除非是刚录入的数据。
SQL77
2010-10-21
打赏
举报
回复
根据需求来呗,如果主键列真的过多,用IDENTITY列还是可以的,貌似我们用的比较少
gdk123
2010-10-21
打赏
举报
回复
看着大家的想法,我觉着自己还没入门,哎。。。
louisit
2010-10-21
打赏
举报
回复
guid,identity用的比较多
Versus1008
2010-10-21
打赏
举报
回复
xiaoxiangqing
2010-10-21
打赏
举报
回复
identity作为主键比较多
fellowcheng
2010-10-21
打赏
举报
回复
guid,identity用的比较多
「已注销」
2010-10-21
打赏
举报
回复
尽量根据实际业务来设定主键
如果实际状况下不太需要主键的话,设定自增列为主键也是不错的建议,应该比没有要好些。
ws_hgo
2010-10-21
打赏
举报
回复
.........
Mr_Nice
2010-10-21
打赏
举报
回复
之前做的项目里面,PK 还是用跟业务相关的Code来定义的。
无意义代码固然有一定的特性,但是具体使用中,数据的可读性会来的更重要一些。
加载更多回复(30)
Sql Server2016从入门到实战应用
本课程全面介绍了sqlserver2016系统的体系架构和功能。本课程以章节的形式,共13章,逐步学习,内容包括sqlserver2016理论知识,建库原理,维护数据库的优缺点、t-sql基础语言、表的创建原理和依据、sql查询,从简单查询入手带着大家一起探讨复杂的业务逻辑sql语句编写方式,关联查询,优化查询,分组排序、视图、索引和游标,
主键
的好处和用法,外键的建立依据、存储过程与触发器、数据库的备份与还原、安全与权限综合知识学习,定时作业计划的
设计
和定制等相关内容详解。本课程
设计
的初衷是从基础知识入门到最后能独立掌握和编写各种业务场景下的sql语句,同时对数据库管理人员来说是一个不错的选择,因为该课程是比较系统性的,不像其他课程一样,只是其中的一些片段。不具备连贯性,对于开发人员来说,该课程在
设计
表的时候,sql查询语句编写的时候,都需要结合实际的开发人员业务场景下来编写,因为我们也是站在开发的角度来讲解和编写课程中的案例。对于实施工程师而言,在客户现场更要注重数据库的安全,从安全和备份还原,定时作业计划的
设计
上来重点分析,总之本课程是目前线上比较全面的,系统的,能帮助大家升职加薪的必须之课。
mysql数据库
主键
如何
设计
mysql数据库
主键
如何
设计
数据库
设计
中是
设计
联合
主键
还是唯一索引+单一
主键
好?
在一个表中user_id和type两个字段唯一确定一条记录,那么在
设计
中是将这两个字段
设计
为联合
主键
呢,还是建立一个逻辑
主键
id,而将这两个字段
设计
为唯一索引呢?这两种方式有什么区别?哪个更好呢?具体还是要看你的业务需求。另外说些在读写操作上的区别:1.
主键
和符合
主键
在查询上没什么性能上的区别(前提是索引相同,运用得当)2.写的性能上是有区别的,因为符合
主键
会使用更多的block去创建索引,所以在
数据库表
主键
设计
原则
阅读《阿里 Java 开发手册》时,有以下 MySQL 建表规约: 表必备三字段:id, gmt_create, gmt_modified。 说明:其中id必为
主键
,类型为unsigned bigint、单表时自增、步长为1。gmt_create, gmt_modified的类型均为date_time类型。 这样的要求似乎是违反数据
设计
的范式的,但既然手册中强调这点就搜索学习了一下这样做
分布式
主键
生成
设计
策略
常见的分布式
主键
生成策略
MS-SQL Server
34,591
社区成员
254,589
社区内容
发帖
与我相关
我的任务
MS-SQL Server
MS-SQL Server相关内容讨论专区
复制链接
扫一扫
分享
社区描述
MS-SQL Server相关内容讨论专区
社区管理员
加入社区
获取链接或二维码
近7日
近30日
至今
加载中
查看更多榜单
社区公告
暂无公告
试试用AI创作助手写篇文章吧
+ 用AI写文章