数据库设计中真的需要外键吗?
据我所知,外键(FK)用于帮助程序员以正确的方式操作数据。假设程序员实际上已经在以正确的方式执行此操作,那么我们真的需要外键的概念吗?
外键还有其他用途吗?我在这里想念什么吗?
解决方案
回答
外键有助于在数据级别上强制执行引用完整性。它们还提高了性能,因为通常默认情况下会对其进行索引。
回答
外键还可以帮助程序员使用诸如ON DELETE CASCADE之类的代码来减少代码编写量。这意味着,如果我们有一个包含用户的表,而另一个包含订单或者某物的表,那么删除该用户将自动删除所有指向该用户的订单。
回答
我无法想象设计没有外键的数据库。没有它们,最终我们必定会犯一个错误并破坏数据的完整性。
从严格意义上讲,它们不是必需的,但是好处是巨大的。
我相当确定FogBugz在数据库中没有外键约束。我很想听听Fog Creek软件团队如何构造代码以保证他们永远不会引入不一致之处。
回答
如果没有外键,我们如何分辨不同表中的两个记录是相关的?
我认为我们指的是参照完整性,即不允许在没有现有父记录的情况下创建子记录等。这些通常称为外键约束,但不要与外键在表中的存在相混淆。第一名。
回答
我们可以将外键视为一种约束,
- 帮助维持数据完整性
- 显示数据如何相互关联(这有助于执行业务逻辑和规则)
- 如果正确使用,可以帮助提高从表中提取数据的效率。
回答
我认为某些时候某些事情必须负责确保有效的关系。
例如,Ruby on Rails不使用外键,但是它会验证所有关系本身。如果我们只从Ruby on Rails应用程序访问数据库,那很好。
但是,如果我们有其他正在写入数据库的客户端,则没有外键,它们需要实现自己的验证。然后,我们将获得验证码的两个副本,这些副本很可能是不同的,任何程序员都应该知道这是一个主要的罪过。
到那时,确实需要外键,因为它们可以让我们将职责再次移至单个点。
回答
Suppose a programmer is actually doing this in the right manner already
在我看来,做出这样的假设是一个非常糟糕的主意。一般而言,软件是令人难以置信的错误。
的确如此。开发人员无法正确解决问题,因此确保数据库中不会填充不良数据是一件好事。
尽管在理想情况下,自然联接将使用关系(即FK约束)而不是匹配列名。这将使FK更加有用。
回答
就个人而言,我赞成使用外键,因为它使表之间的关系正式化。我意识到问题以程序员没有引入会破坏参照完整性为前提的数据为前提,但是我看到了太多的例子,尽管有最好的意图,但这些数据违反了参照完整性。
前外键约束(也称为声明性引用完整性或者DRI)花费了大量时间使用触发器来实现这些关系。我们可以通过声明性约束将关系形式化的事实非常有力。
@John其他数据库可能会自动为外键创建索引,但是SQL Server不会。在SQL Server中,外键关系仅是约束。我们必须分别在外键上定义索引(这很有用。)
编辑:IMO,我想补充一点,使用外键来支持ON DELETE或者ON UPDATE CASCADE不一定是一件好事。在实践中,我发现应该根据数据之间的关系仔细考虑删除的级联-例如我们是否有一个自然的亲子关系,可以正常吗?还是相关表是一组查找值?使用级联更新意味着我们允许修改一个表的主键。在那种情况下,我有一个普遍的哲学分歧,那就是表的主键不应更改。键本质上应该是恒定的。
回答
是的。
- 他们让你诚实
- 他们让新开发者诚实
- 我们可以执行"删除级联"
- 它们可以生成漂亮的图表,这些图表可以自我解释表之间的链接
回答
我们目前不使用外键。在大多数情况下,我们不后悔。
也就是说,由于多种原因,我们可能会在不久的将来开始大量使用它们,而这两个原因都是相似的:
- 图解。如果正确使用了外键关系,那么生成数据库图表就容易得多。
- 工具支持。如果存在适当的外键关系,则使用Visual Studio 2008构建可用于LINQ to SQL的数据模型要容易得多。
所以我想我的意思是,我们发现如果我们在做大量手动SQL工作(构造查询,运行查询,等等),外键不一定是必需的。但是,一旦我们开始使用工具,它们就会变得有用得多。
回答
安全带不是绝对必要的,因此不是绝对必要的。但是它们确实可以使我们免于愚蠢地使数据库混乱。
调试FK约束错误比重新构造破坏应用程序的删除要好得多。
回答
关于外键约束(实际上确实是约束)的最好之处在于,编写查询时可以依靠它们。如果我们不依赖于数据模型为" true",那么很多查询就会变得更加复杂。
在代码中,通常只会在某处引发异常,而在SQL中,通常只会得到"错误"答案。
从理论上讲,SQLServer可以将约束用作查询计划的一部分,但是除了用于分区的检查约束之外,我不能说我曾经亲眼目睹过。
回答
没有FK约束的数据库模式就像没有安全带的驾驶。
有一天,你会后悔的。不花一点额外的时间在设计基础和数据完整性上,无疑是确保以后麻烦的有效方法。
我们会在应用程序中接受如此草率的代码吗?直接访问成员对象并直接修改数据结构。
我们为什么认为在现代语言中这已经变得很难甚至无法接受了?
回答
我从成本/收益方面考虑...在MySQL中,添加约束是DDL的另外一行。这只是几个关键词和几秒钟的思考。我认为这是唯一的"成本"。
工具喜欢外键。外键可防止可能不会影响业务逻辑或者功能的不良数据(即孤立的行),因此不会引起注意并堆积。这还可以防止不熟悉该架构的开发人员实现整个工作块,而又不会意识到他们之间缺少联系。也许在当前应用程序的范围内,一切都很好,但是如果我们错过了某些东西,又有一天又添加了一些意外的东西(想想报告),我们可能就需要手动清理自开始以来就一直在累积的不良数据。无需数据库强制检查的模式。
将事情整理在一起时,花很少的时间整理头脑中已有的内容,可以为我们或者他人节省数月或者数年的痛苦。
问题:
Are there any other uses for foreign keys? Am I missing something here?
它有点加载。插入注释,缩进或者变量名来代替"外键" ...如果我们已经完全理解了所要解决的问题,那么对我们来说"没用"。
回答
我从事过的项目(业务应用程序和社交网站)中从未声明过外键(FOREIGN KEY REFERENCES表(列))。
但是,总是有一种命名列的约定,即外键。
就像数据库规范化一样,我们必须知道自己在做什么以及这样做的结果(主要是性能)。
我知道外键的优点(数据完整性,外键列的索引,知道数据库模式的工具),但我也害怕将外键用作一般规则。
而且,各种数据库引擎可以以不同的方式提供外键,这可能会导致在迁移过程中产生细微的错误。
使用ON DELETE CASCADE删除已删除客户端的所有订单和发票是外观漂亮但设计错误的数据库架构的完美示例。
回答
没有外键是否有好处?除非我们使用糟糕的数据库,否则FK的设置并不难。那么,为什么要制定避免使用它们的政策?命名约定说一列引用另一列是一回事,知道数据库实际上正在为我们验证这种关系是另一回事。
回答
是的。 ON DELETE [RESTRICT | CASCADE]阻止开发人员搁浅数据,保持数据干净。我最近加入了一个Rails开发人员团队,他们不关注外键之类的数据库约束。
幸运的是,我发现了这些内容:http://www.redhillonrails.org/foreign_key_associations.html-Ruby on Rails插件上的RedHill使用约定优于配置样式来生成外键。使用product_id进行迁移将为产品表中的ID创建一个外键。
在RedHill上查看其他出色的插件,包括打包在事务中的迁移。
回答
外键允许以前没有看过我们数据库的人确定表之间的关系。
现在,一切可能都很好,但是请考虑一下,当程序员离职而其他人必须接管时会发生什么。
外键将使他们能够理解数据库结构,而无需遍历数千行代码。
回答
我想我们正在谈论数据库强制执行的外键约束。我们可能已经在使用外键,只是没有告诉数据库。
Suppose a programmer is actually doing this in the right manner already, then do we really need the concept of foreign keys?
从理论上讲,不会。但是,从来没有一款软件没有错误。
应用程序代码中的错误通常并没有那么危险,我们可以识别并修复该错误,然后再使应用程序平稳运行。但是,如果一个错误允许损坏的数据进入数据库,那么我们就被它困住了!从数据库中的损坏数据中恢复非常困难。
考虑一下FogBugz中的一个细微错误是否允许将损坏的外键写入数据库。修正错误并在修正版本中快速将修正推向客户可能很容易。但是,如何解决数十个数据库中的损坏数据?正确的代码现在可能突然中断,因为有关外键完整性的假设不再成立。
在Web应用程序中,通常只有一个程序与数据库对话,因此,只有一个地方错误可能破坏数据。在企业应用程序中,可能有几个独立的应用程序与同一个数据库对话(更不用说直接与数据库外壳一起工作的人了)。没有办法确保所有应用程序都遵循相同的假设,并且始终存在错误。
如果约束是在数据库中编码的,则错误可能发生的最糟糕的情况是,向用户显示关于某些SQL约束未满足的丑陋错误消息。最好将破坏性数据放到企业数据库中,这又将破坏所有应用程序,或者仅仅导致各种错误或者误导性的输出。
哦,外键约束也可以提高性能,因为默认情况下会对其进行索引。我想不出任何理由不使用外键约束。
回答
它们很重要,因为应用程序不是在数据库中处理数据的唯一方法。应用程序可以按需要诚实地处理引用完整性,但是只需一个拥有适当权限的bozo即可在数据库级别发出插入,删除或者更新命令,并且所有应用程序引用完整性强制都将被绕开。将FK约束放在数据库级别意味着,除非在发布命令之前选择禁用此FK约束,否则FK约束将导致错误的insert / update / delete语句失败,并导致参照完整性冲突。
回答
As far as I know, foreign keys are used to aid the programmer to manipulate data in the correct way.
FK允许DBA在程序员未能做到这一点时保护数据完整性,以防止用户感到困惑,有时还可以防止程序员感到困惑。
Suppose a programmer is actually doing this in the right manner already, then do we really need the concept of foreign keys?
程序员是凡人,容易犯错误。 FK是声明性的,这使得它们更难搞砸。
Are there any other uses for foreign keys? Am I missing something here?
尽管这不是创建它们的原因,但是FK为图表工具和查询生成器提供了可靠的可靠提示。这将传递给最终用户,他们迫切需要强大的可靠提示。
回答
FK非常重要,除非我们是eBay,否则FK必须始终存在于模式中。
回答
熵减少。减少数据库中发生混乱情况的可能性。
我们正在考虑所有可能的分子,因此我们很难,因此,我认为,降低熵是维护任何系统的关键。
例如,当我们做一个假设时:每个订单都有一个客户,这个假设应该由某种东西来执行。在数据库中,"某物"是外键。
我认为这值得在开发速度上进行权衡。当然,我们可以在不使用它们的情况下更快地编写代码,这可能就是为什么某些人不使用它们的原因。就我个人而言,我已经使用NHibernate消磨了几个小时,并且某些外键约束在执行某些操作时会很生气。但是,我知道问题出在哪里,所以问题不大。我使用的是常规工具,并且有很多资源可以帮助我解决这个问题,甚至可能有人需要帮助!
另一种选择是允许错误爬入未设置外键且数据变得不一致的系统中(如果有足够的时间,它将进入系统)。然后,我们将得到一个异常的错误报告,进行调查并显示" OH"。数据库被搞砸了。现在要花多长时间才能解决?