2013-04-18 49 views
1

有4個表,每個表都是一個元組ID(INT),name(VARCHAR)(該ID是自動增量的)。有一張餐桌(芝士漢堡,漢堡,肉宴,BLT,番茄湯),班(漢堡,比薩,三明治,湯),特色(辣,素食,無麩質)和麪(沙拉,薯條,麪包) 。很長時間的SQL調用JOIN

三多個表存在,使元組Meal.ID,Class.IDMeal.ID,Characteristics.IDMeal.ID,Sides.ID使得膳食可以是在一個以上的類,有一個以上的特性,並配有一個以上的側,反之亦然。

我有下面的延遲加載就好了,但我們都知道這並不好。我想要的是餐的名稱,它是同一班的特色,餐廳和其他餐點。

此調用工作就好了:

SELECT Group_concat(DISTINCT m2.meal_name SEPARATOR ',')   AS alternates, 
     Group_concat(DISTINCT c.characteristic_desc SEPARATOR ',') AS 
     characteristics 
FROM meal AS M 
     INNER JOIN mealclass AS MC 
       ON M.meal_id = MC.meal_id 
     LEFT JOIN (SELECT meal_id, 
         class_id 
        FROM drugingredient) AS MC2 
       ON MC2.class_id = MC.class_id 
     LEFT JOIN meals AS M2 
       ON MC2.meal_id = M2.meal_id 
     LEFT JOIN mealchar AS MCh 
       ON MCh.meal_id = M.meal_id 
     INNER JOIN characterisics AS C 
       ON C.characteristic_id = MCh.characteristic_id 
WHERE M.meal_id = :meal_id 
     AND M.meal_id <> M2.meal_id 

但是,當我伸出出來這個,我什麼都沒回:

SELECT Group_concat(DISTINCT m2.meal_name SEPARATOR ',')   AS alternates, 
     Group_concat(DISTINCT c.characteristic_desc SEPARATOR ',') AS 
     characteristics, 
     Group_concat(DISTINCT s.sides_desc SEPARATOR ',')   AS side_orders 
FROM meal AS M 
     INNER JOIN mealclass AS MC 
       ON M.meal_id = MC.meal_id 
     LEFT JOIN (SELECT meal_id, 
         class_id 
        FROM drugingredient) AS MC2 
       ON MC2.class_id = MC.class_id 
     LEFT JOIN meals AS M2 
       ON MC2.meal_id = M2.meal_id 
     LEFT JOIN mealchar AS MCh 
       ON MCh.meal_id = M.meal_id 
     INNER JOIN characterisics AS C 
       ON C.characteristic_id = MCh.characteristic_id 
     INNER JOIN mealsides AS MS 
       ON M.meal_id = MS.meal_id 
     INNER JOIN sides AS S 
       ON S.sides_id = MS.sides_id 
WHERE M.meal_id = :meal_id 
     AND M.meal_id <> M2.meal_id 

任何想法如何解決呼叫,或如何有一個更好的架構模式?或者是一定程度的懶惰加載最好的方式去這裏(:P)?!

+0

請掰成行:/ – hjpotter92

+0

檢查mealsides和側面的表,如果有互相Vs之間相應的記錄用餐 – Max

回答

1

有三種可能的事情,你想在這裏。我把它們寫成了一個示範。

create table a (x integer, y integer); 
create table b (v integer, w integer); 
create table c (t integer, u integer); 
insert into a values (1,2); 
insert into a values (3,4); 
insert into a values (5,6); 
insert into b values (1,2); 
insert into b values (5,6); 
insert into c values (1,2); 
insert into c values (3,4); 

這是一樣的,你用:
(A LEFT JOIN B)將C

select * from a left join b on a.x = b.v join c on b.v = c.t; 
x | y | v | w | t | u 
---+---+---+---+---+--- 
1 | 2 | 1 | 2 | 1 | 2 

這將只用左聯接:
(A LEFT JOIN B)LEFT JOIN ç

select * from a left join b on a.x = b.v left join c on b.v = c.t; 
x | y | v | w | t | u 
---+---+---+---+---+--- 
1 | 2 | 1 | 2 | 1 | 2 
3 | 4 | | | | 
5 | 6 | 5 | 6 | | 

認爲這是你瞄準: 一個LEFT JOIN(B JOIN C)

select * from a left join (b join c on b.v = c.t) on a.x = b.v; 
x | y | v | w | t | u 
---+---+---+---+---+--- 
1 | 2 | 1 | 2 | 1 | 2 
3 | 4 | | | | 
5 | 6 | | | | 

希望這有助於

+0

謝謝,這是我完全忘記的左連接! – Richard