将联接的表与其自身联接

时间:2018-10-26 22:16:26

标签: mysql join

我有一个数据库表,字典,它有两个字符串和一个语言ID。

这些列是:

id
product_id
key
translation
language_id

另一张表dictionary_versions,仅包含dictionary_id和翻译版本

id
dictionary_id
version_id

我在表中为每个键有两种不同的翻译,但有时,对于键只有一种翻译。我正在寻找一种获取一种语言的所有翻译,如果有的话,另一种语言ID的翻译的方法。

我希望获得一种language_id和Organizer_id以及一种版本的所有翻译。我试图创建一个临时表,其中包含我要比较的所有值,然后在字典表上对临时表进行左连接,以获取所需语言的所有翻译后的值,以及是否有其他语言的翻译,包括那些。

问题是当两种语言进行10000种翻译时,它变慢。是否有更好的方法将Dictionary_versions表作为两者的where子句将表连接到自身?

SELECT
    d.*
FROM
    dictionary d 
LEFT JOIN
    dictionary_versions dv ON dv.dictionary_id = d.id
LEFT JOIN
    dictionary d2
LEFT JOIN
    dictionary_versions dv2 ON d2.id = dv2.dictionary_id
ON
    d2.key = d.key 
WHERE
    d.product_id = 1 AND dv.version_id = 3
AND
    d.language_id = 1
LIMIT
    0,10 

这是我尝试的查询之一。但是,如果有多个版本,则它将获取fd2表的所有版本,从而导致数据不准确。

我尝试的另一种方法是使用临时表,此方法有效,但速度较慢。这是通过两个查询完成的:

CREATE TEMPORARY TABLE IF NOT EXISTS dictionary_temp_1 
AS (
    SELECT d.* FROM `dictionary` AS `d`
    LEFT JOIN `dictionary_versions` AS `dv` ON dv.dictionary_id = d.id
    WHERE d.product_id = 1 AND dv.version_id = 3 AND d.language_id = 1 
    ORDER BY fd.key ASC LIMIT 0,10 )

第二:

SELECT
    d.key,
    d2.key AS toKey,
    d.translation AS `1`,
    d2.translation AS `2`
FROM
    `dictionary` AS `d`
LEFT JOIN
    `dictionary_versions` AS `dv` ON d.id = dv.dictionary_id
LEFT JOIN
    `dictionary_temp_1` AS `d2` ON d2.key = d.key
WHERE
     d.product_id = 1 AND dv.version_id = 3 AND d.language_id = 1
ORDER BY
     d.key ASC LIMIT 0,10

1 个答案:

答案 0 :(得分:0)

由于@philipxy,我设法找到了一个解决方案作为参考,将我引向this answer供参考。

SELECT d.key, d2.key AS toKey, d.translation AS `1`, d2.translation AS `2`
FROM dictionary d 
INNER JOIN dictionary_versions dv ON dv.dictionary_id = d.id 
LEFT JOIN (
    SELECT d.* 
    FROM `dictionary` AS `d`
    INNER JOIN `dictionary_versions` AS `dv` ON d.id = dv.dictionary_id 
    WHERE d.product_id = 1 AND dv.version_id = 3 AND d.language_id = 2
) d2 ON d2.key = d.key 
WHERE d.product_id = 1 AND dv.version_id = 3 AND d.language_id = 1 

这将在将子查询联接到表本身之前创建一个子查询。这两个表都应用了where条件,因此获得了一个language_id的翻译,并匹配了另一个language_id的翻译(如果存在)。