2013-04-30 19 views
2

我有三個表:如何正確書寫MySQL的子查詢的條件和限制

帖子: ID,標題的AuthorID,文字

作者: ID,姓名,國家

評論: id,authorId,text,postId

我想運行一個mysql命令,它選擇由作者編寫的前5個帖子,其國家是'愛爾蘭'。在同一個電話中,我想檢索這五個帖子的所有評論,以及作者信息。

我已經試過如下:

SELECT posts.id as 'posts.id', posts.title as 'posts.title' (etc. etc. list all fields in three table) 
FROM 
(SELECT * FROM posts, authors WHERE authors.country = 'ireland' AND authors.id = posts.authorId LIMIT 0, 5) as posts 
LEFT JOIN 
comments ON comments.postId = posts.id, 
authors 
WHERE 
authors.id = posts.authorId 

我必須包括用別名^每場因爲沒有爲ID重複,並在今後更多的領域可能成爲我在尋找重複通用的解決方案。

我的兩個問題是:

1)我正在從我的子查詢的ID內的重複字段項,所以我必須在子查詢中再次列出我的所有字段的別名或有隻有一個我需要一個子選擇

2)有沒有辦法來自動別名我的電話?目前,我只是在主選擇中爲每個字段設置了別名,但是它可以爲我做到這一點,所以沒有重複?

對不起,如果這不是很清楚,這是一個混亂的問題!謝謝。

回答

2

您正在執行不必要的連接回到查詢中的author表。您可以在posts子查詢中獲得所有的字段。我會將此重命名爲除現有表以外的其他內容,可能是pa以指示帖子和作者。

你說你想要前5個職位,但沒有訂單條款。查詢的更好形式是:

SELECT pa.id as 'posts.id', pa.title as 'posts.title' (etc. etc. list all fields in three table) 
FROM (SELECT * 
     FROM posts join 
      authors 
      on authors.id = posts.authorId 
     WHERE authors.country = 'ireland' 
     order by post.date 
     LIMIT 0, 5 
    ) pa LEFT JOIN 
    comments c 
    ON c.postId = pa.id 

請注意,這將返回前五個帖子及其作者(如問題中指定的)。但有一位作者可能負責所有五個職位。

在MySQL中,您可以使用*,它將刪除from子句中的重複別名。我認爲這是危險的。列出你想要的所有列最好。

+0

謝謝!關於第二次不必要的連接,並忘記了命令日期:p在子選擇中,SELECT *不會導致'Mysql錯誤:重複列名'id'',因爲作者和帖子都有一個id? – user1020317 2013-04-30 16:14:50

+0

另外,ID我只在我的子選擇中選擇了posts.id,這是否意味着我只能在主語句中訪問該職位的ID? – user1020317 2013-04-30 16:16:35

+0

@ user1020317。 。 。是。然後你必須回到'authors'表中來獲得這些字段。 – 2013-04-30 16:20:25

1

回答您的問題:

  1. 您可以選擇儘可能多(或儘可能少)列當你從一個子查詢需要
  2. 你並不需要已經重新加入authors表,因爲你選擇子查詢中的所有字段(並刪除重複的列名稱)。

補充幾點......

......有關JOIN語法

偏好的形式

FROM t1 JOIN t2 ON (t1.fk = t2.pk) 

到過時的,模糊的

FROM t1, t2 WHERE t1.fk = t2.pk 

......關於使用LIMIT條款沒有ORDER BY條款

行由0123返回的順序聲明沒有ORDER BY子句是未定義的。因此,在理論上,沒有ORDER BY子句的LIMIT n子句可以返回任何行。

你最終的查詢應該是這樣的:

SELECT * 
FROM (
    SELECT * 
    FROM posts 
    JOIN authors ON (authors.id = posts.authorId) 
    WHERE authors.country = 'ireland' 
    ORDER BY posts.id DESC -- assuming this column is monotonically increasing 
    LIMIT 5 
) AS last_posts 
LEFT JOIN comments ON (comments.postId = last_posts .id)