在mysql中填充/加入多对多关系表的多个表

时间:2019-03-14 10:13:09

标签: mysql join

这个问题应该已经问过,但是我发现很难找到。 我有表usersallergiesdietaries。用户可能有多种过敏和多种饮食习惯。因此,我有user_allergiesuser_dietaries表,它们存储两个表的外键。

现在,我想显示用户列表及其相应的过敏症,饮食名称。我试过这样的左联接->

SELECT
    users.user_id as 'id',
    IFNULL(CONCAT(users.first_name,' ',users.last_name),'') as 'name',
    IFNULL(GROUP_CONCAT(allergies.title),'') as 'allergies'
FROM (users
    LEFT JOIN user_allergies
        ON users.user_id = user_allergies.user_id
    LEFT JOIN allergies
        ON user_allergies.allergies_id = allergies.allergies_id
      )
GROUP BY users.user_id;

响应完全像我想要的那样->

7 | Khabib Nurmagamedov | Milk,Corn
8 | Conor Mcgregor      | Milk,Corn

现在,我希望以相同的方式获取dietaries。所以我类似地为饮食添加了Left Join->

SELECT
    users.user_id as 'id',
    IFNULL(CONCAT(users.first_name,' ',users.last_name),'') as 'name',
    IFNULL(GROUP_CONCAT(allergies.title),'') as 'allergies',
    IFNULL(GROUP_CONCAT(dietaries.title),'') as 'dietaries'
FROM (users
    LEFT JOIN user_allergies
        ON users.user_id = user_allergies.user_id
    LEFT JOIN allergies
        ON user_allergies.allergies_id = allergies.allergies_id
    LEFT JOIN user_dietaries
        ON users.user_id = user_dietaries.user_id
    LEFT JOIN dietaries
        ON user_allergies.allergies_id = dietaries.dietaries_id
      )  
GROUP BY users.user_id;

但是现在我得到的输出->

7 | Khabib Nurmagamedov | Milk,Corn,Eggs,Meat | Milk,Corn,Eggs,Meat
8 | Conor Mcgregor      | Milk,Corn,Eggs,Meat | Milk,Corn,Eggs,Meat

应该是->

7 | Khabib Nurmagamedov | Milk,Corn | Eggs,Meat
8 | Conor Mcgregor      | Milk,Corn | Eggs,Meat

我在这里苦苦挣扎。我该怎么办? 提前谢谢。

编辑: 回应是->

7 | Khabib Nurmagamedov | Milk,Corn,Milk,Corn | Milk,Milk,Corn,Corn
8 | Conor Mcgregor      | Milk,Eggs,Milk,Eggs | Milk,Milk,Corn,Corn

我认为两个表数据都被连接起来了,但是结果显然出现了两次。 结果必须为->

7 | Khabib Nurmagamedov | Milk,Corn | Milk,Corn
8 | Conor Mcgregor      | Milk,Eggs | Milk,Corn

2 个答案:

答案 0 :(得分:1)

您的问题是,您希望将GROUP_CONCAT放在2个单独的列中,并且那样行不通。

您必须从用户表中将group_concat结果加入2次:

SELECT u.user_id as 'id',
             IFNULL(CONCAT(u.first_name,' ',u.last_name),'') as 'name',
             ua.allergies_c as 'allergies',
             ud.dietaries_c as 'dietaries'
FROM users u
LEFT JOIN
    (
        SELECT
            users.user_id ,
            IFNULL(GROUP_CONCAT(allergies.title),'') as allergies_c
        FROM (users
            LEFT JOIN user_allergies
                ON users.user_id = user_allergies.user_id
            LEFT JOIN allergies
                ON user_allergies.allergies_id = allergies.allergies_id
              )
        GROUP BY users.user_id
    ) ua ON u.user_id=ua.user_id
LEFT JOIN
    (
        SELECT
            users.user_id,
            IFNULL(GROUP_CONCAT(dietaries.title),'') as dietaries_c
        FROM (users
            LEFT JOIN user_dietaries
                ON users.user_id = user_dietaries.user_id
            LEFT JOIN dietaries
                ON user_dietaries.dietaries_id = dietaries.dietaries_id
              )
        GROUP BY users.user_id
    ) ud ON u.user_id=ud.user_id

我做了一些大规模替换,以便更快地进行,您可能需要修复一些问题,但是想法就在那里了。

答案 1 :(得分:0)

通过在allergies.title和Dietaries.title之前添加Distinct,我可以获得我想要的结果。 但不确定为什么标题字段会出现两次。

SELECT
    users.user_id as 'id',
    IFNULL(CONCAT(users.first_name,' ',users.last_name),'') as 'name',
    IFNULL(GROUP_CONCAT(Distinct allergies.title),'') as 'allergies',
    IFNULL(GROUP_CONCAT(Distinct dietaries.title),'') as 'dietaries'
FROM (users
    LEFT JOIN user_allergies
        ON users.user_id = user_allergies.user_id
    LEFT JOIN allergies
        ON user_allergies.allergies_id = allergies.allergies_id
    LEFT JOIN user_dietaries
        ON users.user_id = user_dietaries.user_id
    LEFT JOIN dietaries
        ON user_allergies.allergies_id = dietaries.dietaries_id
      )  
GROUP BY users.user_id;