2009-02-03 30 views
12

我们有今天早上有关如何将应存储我们的ID为我们制作了一些资产,我们已经在我们的数据库中,descusion产生一点点热量,所以我决定来咨询的SO专家会议。为主键使用项目特定的前缀和自动编号?

表结构即我相信,我们应该有(短版)是这样的:

实施例1)

  • 由assetid - INT(32) - 主键
  • 类型 - 字符串

所以一些示例数据是这样的:

==AssetId======Type=== 
    12345  "Manhole" 
    155415  "Pit" 

团队的另一名成员建议是这样的:

例2)

  • 由assetid - 字符串 - 主键
  • 类型 - 字符串

所以一些示例性数据是这样的:

==AssetId======Type=== 
    "MH12345" "Manhole" 
    "P155415" "Pit" 

,我们做的那种类型的短版本,并将它附加到ID的前面,并将其存储在数据库中。我见过一些资产数据库可以做到这一点,并且从来没有真正采用这种方法。

我从来没有真正喜欢使用字符串为排列原因ID的想法。无论如何,当您已经拥有资产商店类型时,我也觉得它只是为了存储无用的信息。

你会采取什么方法?为什么?使用2号方法1有什么好处?

编辑:是的,我将使用AUTO_INCREMENT的方法1.

+0

似乎有几个答案 - 包括当前接受的答案 - 误解了例2作为自然主键,即包含实际业务数据的键。也许你可以稍微澄清一点,因为示例2中的键似乎只是代理键 - 它们与行的业务数据没有关系 - 但带有额外的表指定前缀。 – 2009-12-18 06:44:08

回答

25

通常,经验法则是永远不要在主键中使用有意义的信息(如社会安全号码或条形码)。只是普通的自动增量整数。不过,数据看起来不变 - 它可能会在一个点上发生变化(新的立法出现,所有的SSN都会重新计算)。

+2

是的!在过去的三家公司中,我曾经因为一些白痴选择了一个“自然”的钥匙而遭受了很大的痛苦。 UPC被回收;不是每个人都有一个SSN;人们搞砸了创造SKU。你存储它,你可以独特它,但PK是你的关系的秘密号码。你不要暴露它。 – 2009-02-26 05:41:03

4

我会去前。创建唯一ID应留给SQL服务器,如果它们是字符串,则不能以线程安全方式自动创建这些ID。根据我的理解,你不得不自己处理这个问题?

速度是另一个因素。处理int值始终会比字符串更快。我会说,大约有索引等PERF的好处,更加精明的SQL比人可能我详细阐述;)

以我的经验,有字符串ID已经失效。

2

我个人认为第一种方法是远远更好。它可以让数据库软件进行简单的整数比较以找到并按键进行排序,这将提高表操作性能(SELECT,复杂JOIN,按键INDEX查找等)。)

当然,我假设无论哪种方式,您正在使用某种自动递增方法来生成ID - 序列,AUTO_INCREMENT或类似的东西。帮我一个忙,不要在程序代码中创建这些代码,好吗?

+0

是的我会使用AUTO_INCREMENT的方法1.(添加到帖子) – 2009-02-03 06:34:02

7

这是surrogate and natural keys之间的决定,第一个是代理(或“技术”),第二个是自然的。

我得出结论,你应该几乎总是使用代理键。如果你使用自然键,那些可能会改变,更新主键/外键通常不是一个好主意。

+0

这是一个有趣的观点,但它不回答这个问题,因为例子1和2都是代理键。 ;-) – 2009-12-17 16:25:53

0

如果您的资产已具有唯一的自然标识符(例如员工及其员工标识),请使用它们。创建另一个唯一标识符没有意义。另一方面,如果没有自然唯一的ID,则使用最短的那个ID来确保预期的表大小足够(例如整数)。它需要更少的磁盘空间,可能会更快。此外,如果您发现自己需要稍后使用基于字符串的密钥,则这是一个简单的替换作业:

  • 将资源表的主键添加到资产表。
  • 将字符串外键添加到引用表中。
  • 使用整数关系更新与简单UPDATE命令的字符串关系。
  • 为sting列添加外键约束。
  • 删除整数列的外键约束。
  • 完全删除整数列。

其中某些步骤可能在特定DBMS上有问题,可能需要使用表卸载/重新加载来删除整数主键列,但该策略基本上是需要的。

3

嗯,我想使一些要点和建议,

  • 考虑为一类单独的表,说与列标识和说明,然后做一个外键TYPEID此表。为了使事物正常化更进一步。但它可能并不理想。如果你认为它服务于某种目的,那就去做吧

  • 如果以后你们想到转向UUID,那么使它成为字符串是有意义的。你并不需要更改数据类型,然后

[编辑]

我克莱图斯这里同意。这个代理关键证明在一些现实生活中是有益的。他们允许改变,而且你很清楚,改变是唯一不变的。

1

我更喜欢示例1,因为您提到的原因,我可以想到的使用示例2的唯一参数是如果您尝试从现有数据库容纳字符串ID(很常见),但即使在该场景中,我宁愿使用以下方法。

==AssetId(PK)==Type========DeprecatedId==== 
    12345  "Manhole" "MH64247" 
    155415  "Pit"  "P6487246" 
0

示例2的唯一优点是,只需从主键就可以轻松判断出该键适用于哪个表的哪一行。这个想法很好,但它是否有用取决于您的日志记录和错误消息策略。它可能有一个性能上的缺点,所以我不会使用它,除非你能指出为什么要使用它的一些具体原因。 (你也可以通过使用全局序列来生成数字键,或者通过使用不同的数字范围,最后一位数字或其他值来获得这个优势,那么你没有性能上的缺点,但是也许你找不到表很容易。)

3

我会选择数字主键出于性能原因。整数比较比字符串比较便宜得多,并且它将在数据库中占用较少的空间。