INT与数据库中ID字段的唯一标识符

mkc*_*ler 33 sql t-sql sql-server uniqueidentifier

我正在使用SQL Server 2005(可能在不久的将来使用SQL Server 2008)为网站创建一个新数据库.作为一名应用程序开发人员,我见过很多数据库使用integer(或bigint等)表格的ID字段来用于关系.但最近我也看到了使用unique identifier(GUID)作为ID字段的数据库.

我的问题是,一个人是否优于另一个人?将integer字段是查询和连接等快?

更新:为清楚起见,这是表中的主键.

Rem*_*anu 52

由于随机性较高,GUID作为群集密钥存在问题.Paul Randal在上一期Technet杂志问答专栏中解决了这个问题:我想使用GUID作为聚簇索引键,但其他人则认为它可能导致索引的性能问题.这是真的,如果是的话,你能解释一下原因吗?

现在请记住,讨论具体是关于聚簇索引.您说您希望将该列用作"ID",如果您将其表示为群集密钥或仅仅是主键,则不清楚.通常两者重叠,所以我假设你想将它用作聚簇索引.在上面提到的文章的链接中解释了为什么这是一个糟糕的选择的原因.

对于非聚簇索引,GUID仍然存在一些问题,但不像它们是表的最左侧聚簇键时那么大.同样,GUID的随机性引入了页面拆分和碎片,只是在非聚集索引级别(一个小得多的问题).

围绕GUID使用的许多城市传说基于它们的大小(16字节)与int(4字节)相比来谴责它们,并且如果使用它们则承诺可怕的性能厄运.这有点夸张.在正确设计的数据模型上,16号键可以是一个非常有用的键.虽然如果它是int的4倍大,会导致索引中的密度更低的非叶页面,这对于绝大多数表来说并不是真正的问题.b树结构是一个自然平衡的树,树遍历的深度很少是一个问题,因此基于GUID键而不是INT键寻找值在性能上是相似的.叶页遍历(即表扫描)不查看非叶页,GUID大小对页面大小的影响通常非常小,因为记录本身明显大于引入的额外12个字节由GUID.因此,我会采用基于'16字节对4'的听说建议,使用相当大的盐.逐个案例分析个别情况,并确定大小影响是否真正产生影响:表中有多少其他列(即叶子页面上GUID大小有多大影响)以及有多少引用正在使用它(即.有多少其他表会因为需要存储更大的外键而增加.

我正在以一种临时防御GUID的方式调出所有这些细节,因为他们最近收到了很多不好的报道,有些是不应该的.它们有其优点,在任何分布式系统中都是必不可少的(当你谈论数据移动时,无论是通过复制或同步框架还是其他).我看到根据GUID在没有适当考虑的情况下避开的不良声誉做出的错误决定.但确实如此,如果必须使用GUID作为集群密钥,请确保解决随机性问题:尽可能使用顺序guid.

最后,回答你的问题:如果你没有特定的理由使用GUID,请使用INT.

  • 如果您有聚集索引,请使用 NEWSEQUENTIALID()。 (2认同)

JBr*_*oks 8

即使您使用newsequentialid()函数,GUID也会占用更多空间并且比int慢.如果您要复制或使用同步框架,您几乎必须使用guid.


Phi*_*ley 6

INT是4个字节,BIGINT是8个字节,GUIDS是16个字节.表示数据所需的空间越多,处理数据所需的资源就越多 - 磁盘空间,内存等.因此(a)它们的速度较慢,但​​(b)这可能只是因为卷是一个问题(数百万)在非常非常短的时间内进行行或数千次交易.)

GUID的优势在于它们(几乎)是全球唯一的.使用正确的算法生成一个guid(并且SQL Server xxxx将使用正确的算法),并且没有两个guid将是相似的 - 无论生成它们的计算机有多少,无论多么频繁.(这在使用72年后不适用 - 我忘记了细节.)

如果您需要跨多个服务器生成唯一标识符,则GUID可能很有用.如果你需要mondo perforance和不到20亿的价值,那么整数可能就好了.最后也许最重要的是,如果您的数据具有自然键,请坚持使用并忘记代理值.


Jac*_*tti 5

如果你肯定,绝对必须有一个唯一的ID,然后GUID。这意味着如果您要合并、同步、复制,您可能应该使用 GUID。

对于不太健壮的东西,一个 int 应该就足够了,这取决于表的增长大小。

在大多数情况下,正确的答案是,视情况而定。