[英]Creating a SQL statement based on a column enum value
Let's assume I have a table called normalize with an enum column called type 假设我有一个名为normalize的表,该表带有一个名为type的枚举列
Depending on the row (Let's assume the types are a, b or c) I want to do a LEFT JOIN based on whatever the type is. 根据行的不同(让我们假设类型是a,b或c),我想基于任何类型进行LEFT JOIN。
So, if type = a, LEFT JOIN ON table a .. if type = B, LEFT JOIN ON table b... etc 因此,如果类型= a,则在表a上为LEFT JOIN ON ..如果类型= B,则在表b上为LEFT JOIN ON ...等等
Can this be done efficiently? 可以有效地做到这一点吗? Or should this be done at the application layer? 还是应该在应用程序层完成?
Yes, you should be able to do something like this: 是的,您应该可以执行以下操作:
SELECT *
FROM parent
LEFT JOIN a ON (type = 'a' AND parent.id = a.id)
LEFT JOIN b ON (type = 'b' AND parent.id = b.id)
LEFT JOIN c ON (type = 'c' AND parent.id = c.id)
You may or may not need an index on type
, depending on the actual data and how smart your DBMS is (in exploiting indexes that ought to exist underneath PKs). 您可能需要也可能不需要type
索引,具体取决于实际数据和DBMS的智能程度(利用PK下应存在的索引)。 In any case, measure on realistic amounts of data. 无论如何,都要根据实际数据量进行度量 。
One common approach is to store the type as a 1:1 relation. 一种常见的方法是将类型存储为1:1关系。 In this approach, there is no type enum column. 在这种方法中,没有类型枚举列。 The fact that an ID is present in a 1:1 extension table indicates its type. 1:1扩展表中存在ID的事实表示其类型。
select *
from BaseTable b
left join
Type1Table t1
on t1.Id = b.Id
left join
Type1Table t2
on t2.Id = b.Id
So an entity with an entry in b
and t1
must be of type 1. An entity with an entry in b
and in t2
is of type 2. That way, the information is only stored once, and an inconsistency where the table would say "type 1" but there was no matching row in t1
is impossible. 因此,在b
和t1
具有条目的实体必须是类型1。在b
和t2
具有条目的实体必须是类型2。这样,信息仅存储一次,并且表中的不一致之处是“类型1”,但在t1
没有匹配的行是不可能的。
The problem is that even if you use SELECT table1.* FROM table1 LEFT OUTER JOIN table2
, the engine will evaluate the join even though you don't even need to show them. 问题在于,即使您使用SELECT table1.* FROM table1 LEFT OUTER JOIN table2
,即使您甚至不需要显示连接,引擎也会评估连接。
So, in my opinion there are 2 options: 因此,我认为有两种选择:
** SEE BELOW, WITHIN THE LIST IT BUGS ** **在清单中发现以下错误**
Explain plan also could give you a good clue of what you're doing 说明计划也可以为您提供一个很好的线索
Query: 查询:
SELECT
IF(t.type = a, ta.value,
IF(type = b, tb.value, IF(type = c, tc.value, td.value))
)
FROM
table t
LEFT JOIN type_a_table ta ON t.type = a AND ...
LEFT JOIN type_a_table tb ON t.type = b AND ...
LEFT JOIN type_a_table tc ON t.type = c AND ...
LEFT JOIN type_a_table td ON t.type = d AND ...
Not sure if this helps, but I would probably use a union to perform what you're looking for 不确定这是否有帮助,但是我可能会使用联合来执行您要查找的内容
select *
from BaseTable b left join TypeTableA a on b.id = a.id
union
select *
from BaseTable b left join TypeTableB b on b.id = b.id
声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.