繁体   English   中英

使用大量可能的连接进行查询的最佳方法

[英]Best way to do a query with a large number of possible joins

在我正在开发的项目上,我们有一个活动表,每个活动都可以链接到大约20个不同的“活动细节”表中的一个......

例如,如果活动是“工作”类型,那么它将具有相应的activity_details_ 工作记录,如果它是“病假”类型,那么它将具有相应的activity_details_ sickleave记录,依此类推。

目前我们正在加载活动,然后对于每个活动,我们都有一个单独的查询来从相关表中获取活动详细信息。 如果你有成千上万的活动,这显然不能很好地扩展。

所以我最初的想法是有一个查询来获取活动并一次性加入细节,例如

SELECT * FROM activity
LEFT JOIN activity_details_1_work ON ...
LEFT JOIN activity_details_2_sickleave ON ...
LEFT JOIN activity_details_3_travelwork ON ...
...etc...
LEFT JOIN activity_details_20_yearleave ON ...

但这会导致每个记录都有100个字段,其中大部分都是空的,感觉很讨厌。

延迟加载细节实际上并不是一个选项,因为细节几乎总是在核心逻辑中被请求,至少对于主要类型而言。

有没有一种超级巧妙的方式来做到这一点,我没想到?

提前致谢

我的建议是为每个ActivityType定义一个视图,该视图专门针对该活动进行定制。

然后在ActivityType字段的Activity表引线上添加一个索引。 集群表示索引,除非对其他一些集群的压倒性需求(或性能基准测试显示其他一些集群选择更高效)。

是否有一个特殊的原因可以解释为什么这种程度的非规范化? 这个原因众所周知吗?

有可能你的活动表就像(date_from, date_to, with_who, descr)或类似的东西。 正如Pieter建议的那样,考虑在那里抛入一个类型varchar或enum字段,以便处理单个详细信息表。

如果有合理的理由保持表格分开,可以考虑添加维护boolean / tinyint字段( has_workhas_sickleave等)或位字符串的has_activites_of_typehas_activites_of_type ,其中第一个位置等于has_workhas_sickleave旁边等) 。

无论哪种方式,通过在一个或多个单独的查询中获取活动的详细信息,您可能会更好 - 如果只是为了避免字段名称冲突。

我不认为枚举是可行的方法,因为正如你所说,可能有1000个活动,然后改变你的activity表将成为一个问题。

没有必要在大量表上进行左连接。

所以你有的选择是:

  1. 看到这个第一条评论可能有用。

  2. 我猜你的活动表有一个名为activity_type_id的字段。 构建一个名为activity_types的表,其中包含字段activity_type_idactivity_nameactivity_details_table_name 首先以下列方式查询

    活动
    内部联接
    activity_types
    使用(activity_type_id)

此查询为您提供要查询详细信息的表名。 这样,您只需在activity_types表中添加一行即可添加任何新的活动类型。

暂无
暂无

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM