我有一个汽车分类列表数据库。
90天后,分类列表不再有效显示(列表过期);但是,我想保留列表以便存档。
问题:从数据库设计最佳实践角度以及查询效果来看,最好将旧列表 A)保留在与当前列表相同的表中或 B),将过期的商家信息移至过期的表格并从当前商家信息表格中删除该商家信息?
换句话说,
选项 A):
table_classified_listing:
car_id
expired = true | false
...
选项 B):
// only current listing in this table (expired = false)
table_classified_listing:
car_id
...
// only expired listing in this table (expired = true)
expired_table_classified_listing:
car_id
...
更新:
我对选项A的关注是,在我的MySQL数据库中 - 当我运行EXPLAIN
时,它说它使用expired
作为索引的主键。但是,对我的查询搜索性能更重要的是它使用price
字段,因为我正在基于price > X
进行搜索。因此,为什么我考虑选择选项B.
答案 0 :(得分:6)
选项A)这样您可以将所有数据放在一个位置,并且可以更轻松地创建查询报告,列出用户历史条目等。任何速度问题都应该通过该列上的数据库索引来缓解。选项B)是premature optimisation。
答案 1 :(得分:4)
一般建议(你必须填补空白;-)):
性能只会在某些情况下显着(超过一百万条记录,行数大......)。
您会使用“联盟”或相同的查询查询两个表吗?如果您不使用相同的查询查询表格,那么我建议使用不同的表格(随着记录数量的增长可能会增加性能,但主要是含义增益)。
重复的问题是它可能会增加工作量(编写查询,测试它们......)。但是所有技术(尤其是现代技术)都允许您减少或取消重复。
例如,使用ORM,您可以拥有一个抽象实体,该实体映射到公共字段但没有表,以及两个映射到表的子类。没有重复的列信息。 ORM也可以创建你的数据库脚本,所以你甚至没有这些(虽然你应该手动查看它们的生产数据库)。
更新:
您可以创建所需的索引,不用担心。如果您正在寻找它以查询超过X的价格未过期的数据,请创建一个索引(已过期,价格),您就可以了: - )
答案 2 :(得分:3)
不要使用B,它基本上是拆分属性。
我要做的就是基本上使用两个日期列。 ValidFromDate和ValidToDate。
答案 3 :(得分:2)
按照你所描述的那样累积列表的速度,性能会降低很长一段时间。并且硬件和软件性能提高得更快。
在你确定需要它之前不要做一些复杂的事情,简单的事情就行不通。把它放在一张桌子里。请参阅有关pessimizations的问题 - 这是一个。
答案 4 :(得分:1)
就我个人而言,我会说把所有过期的那些移到一个单独的表中。随着数据库的增长,您将希望从“实时”记录中获得更好的性能,因为这些记录可能会受到最频繁的影响。
所有旧记录都会导致表格大小不断增长,这意味着查询速度变慢,即使查询优化也是如此。
编辑: 正如其他人提到的那样,如果您计划经常组合实时数据和存档数据,那么这种方法的一个重要方面就是如此。如果你总是单独引用它们而不是很好,但如果没有,你将需要大量的连接和联合将数据拉到一起 - 这是不理想的。
答案 5 :(得分:1)
对于保留旧数据的一般问题,至少还有两个选项:
回到你提供的两个解决方案:
答案 6 :(得分:1)
以下是我的理解:
如果我理解上述内容,下一个问题是您使用过期数据的频率是多少?它用于什么?就像@ghills指出的那样,sql-unions可能会让你失望。
如果过期数据不需要联机,则将其存档到单独的表中可能是有意义的。特别是如果过期行的数量超过活动行数#。
如果将它们保存在同一个表中,“where expired = false”可能最终成为您的常量伴侣,并且由于选择性将很低(即大量过期行),“过期”列上的索引将无法获取你赚了很多钱。 (Oracle有位图索引 - 但这可能根本不适用于此处。)
答案 7 :(得分:1)
我会把它们放在一张桌子里。否则,(a)您有两个具有相同列的表。每当您对数据进行更改时,您都必须记住以相同的方式更改两个表。迟早有人会忘记 - 或者明白一个表中的数据在另一个表中是不需要的 - 而现在你的设计变得更复杂了。很快你就会写两次完全相同的逻辑:一次从“当前”表中检索并再次从“归档”表中检索。但是后来有人对一段代码进行了更改,并忘记对另一段代码进行相同的更改。然后下一个出现的人不能确定他们是否不同,因为有充分的理由说明他们应该是不同的,或者有人忘了。等等(b)看起来你可能会想要查看两个表格的查询,例如“告诉我过去12个月内要价超过20,000美元的所有广告”,其中一些广告可能是最新的,其他广告可能是最新的存档。这些查询现在是联合或复杂的联接,而不是简单地不包括“expired is true”或“expired is false”标记。
关于性能问题,这很简单:创建一个包含您需要包含的内容的多字段键。过期+价格或过期+ modelname似乎很可能是关键。您可能希望首先过期,因为您的大多数查询可能都需要非过期记录,但我只是猜测。选择值得索引的是一个复杂的决策,但是当在多个字段上有明显的常见查询时,就这样做。
答案 8 :(得分:0)
没有通用的最佳实践。但是,如果表格趋于变大并且您的搜索花费了太多时间,那么您可能需要将项目存档在单独的表格或soo中。其他方面,您可以实现正确的索引,也可以使事情更快。这实际上取决于您正在考虑的数据量和类型。