2010-08-20 79 views
85

我想在union查詢中使用order by。 我根據不同的標準從基於距離的表格中獲取不同類型的記錄,以便在我的網站上進行搜索。 第一個選擇查詢返回與確切地點搜索相關的數據。 第二個選擇查詢返回距離搜索地點5公里內距離的數據。 第三個選擇查詢返回距離搜索地點5-15公里內距離的數據。在mysql中使用union和order by子句

然後,我使用union來合併所有結果並在頁面上顯示分頁。在適當的標題爲「精確搜索結果」「結果內5公里」

現在我想根據ID或add_date到結果排序。但是,當我在我的查詢(查詢1聯合查詢2聯合查詢3由add_date順序)的末尾添加order by子句時。它對所有結果進行排序。但是我想要的是它應該在每個標題下排序。

+0

您想在每個表格中排序的字段是什麼類型? – user151841 2010-08-20 13:32:52

回答

163

您可以通過添加一個僞列命名等級給每個做這個選擇,你可以通過先進行排序,通過你的其他標準進行排序之前,例如:

select * 
from (
    select 1 as Rank, id, add_date from Table 
    union all 
    select 2 as Rank, id, add_date from Table where distance < 5 
    union all 
    select 3 as Rank, id, add_date from Table where distance between 5 and 15 
) a 
order by rank, id, add_date desc 
+0

嗨,謝謝你,我正是用這種方式。但我想要的是,我想按降序排列選擇基於add_date的查詢結果。 – Aditya 2010-08-20 16:40:14

+0

你可以使用'desc'關鍵字。我更新了上面的查詢。 – RedFilter 2010-08-20 16:46:28

+0

我只是對代碼進行了快速更改,結果非常棒。你讓我今天一整天都感覺很好。謝謝 – Aditya 2010-08-21 04:52:57

0

嘗試:

SELECT result.* 
FROM (
[QUERY 1] 
UNION 
[QUERY 2] 
) result 
ORDER BY result.id 

其中[查詢1]和[查詢2]是要合併的兩個查詢。

0

這是因爲你的排序整個結果集,您應該單獨排序,聯盟的每一個部分,或者您可以使用ORDER BY(有什麼即子查詢距離)THEN(即東西行ID)子句

4

聯合查詢只能有一個主ORDER BY條款,IIRC。爲了解決這個問題,在構成更大的UNION查詢的每個查詢中,添加一個字段,該字段將是您爲UNIONORDER BY排序的一個字段。

例如,您可能會有諸如

SELECT field1, field2, '1' AS union_sort 
UNION SELECT field1, field2, '2' AS union_sort 
UNION SELECT field1, field2, '3' AS union_sort 
ORDER BY union_sort 

union_sort字段可以是您可能要排序什麼。在這個例子中,它偏偏把結果從第一個表第一,第二臺第二等

38

您可以使用子查詢做到這一點:通過

select * from (select values1 from table1 order by orderby1) as a 
union all 
select * from (select values2 from table2 order by orderby2) as b 
+1

Tnx,很好的一個分開訂單。此外,我們可以有不同的安排如果訂單條款是常見的,但我們想要的結果分離(而不是分離的訂單): 'SELECT * FROM( SELECT AAA AS上校,1官方FROM表1 UNION ALL SELECT BBB作爲官員,0作爲官員從表2 )AS tbl ORDER BY Official,Col' – Alix 2013-12-12 13:21:53

+6

這是[不正確](http://dev.mysql.com/doc/refman/5.7/en/union.html):*對單個'SELECT'語句使用'ORDER BY'意味着在最終結果中行出現的順序沒有任何意義。* – shmosel 2016-03-22 19:05:28

+0

你是對的,接受的答案也是正確的。當我測試它時,這恰好運行良好。 – rickythefox 2016-03-29 16:29:03

0

我嘗試添加的順序給每個工會之前的查詢如

(select * from table where distance=0 order by add_date) 
union 
(select * from table where distance>0 and distance<=5 order by add_date) 

但它似乎沒有工作。它實際上並沒有在每個選擇的行內進行排序。

我認爲你將需要在外面用,東西以保持秩序,並添加列在where子句中的順序一樣

(select * from table where distance=0) 
union 
(select * from table where distance>0 and distance<=5) 
order by distance, add_date 

這可能是一個有點棘手,因爲你想要按範圍分組,但我認爲它應該是可行的。

+0

user151841 union_sort下面的想法將是一個很好的方式來處理分組 – 2010-08-20 14:10:53

2

我得到了這個工作加入聯盟。

(SELECT 
    table1.column1, 
    table1.column2, 
    foo1.column4 
FROM table1, table2, foo1, table5 
WHERE table5.somerecord = table1.column1 
ORDER BY table1.column1 ASC, table1.column2 DESC 
) 

UNION 

(SELECT 
    ... Another complex query as above 
) 

ORDER BY column1 DESC, column2 ASC 
23
(select add_date,col2 from table_name) 
    union 
(select add_date,col2 from table_name) 
    union 
(select add_date,col2 from table_name) 

order by add_date 
+0

這工作,但奇怪我需要改變一件事:我需要給按排序的字段共享別名。除此之外,謝謝! – HoldOffHunger 2016-09-13 23:57:34

6

不要忘記,UNION ALL是將記錄添加到記錄集不排序或合併(與工會)的方式。

因此,例如:

select * from (
    select col1, col2 
    from table a 
    <....> 
    order by col3 
    limit by 200 
) a 
union all 
select * from (
    select cola, colb 
    from table b 
    <....> 
    order by colb 
    limit by 300 
) b 

它使各個查詢更清晰,讓您在每個查詢不同的參數來進行排序。然而,通過使用所選答案的方式,可能會變得更加清晰,具體取決於複雜性以及數據的相關程度,因爲您將這種排序概念化。它還允許您將人工列返回給查詢程序,以便它具有可以排序或組織的上下文。

但是這種方式具有快速的優點,不會引入額外的變量,並且可以很容易地分離出包括排序在內的每個查詢。增加限制的能力只是額外的獎勵。

當然,可以隨意將union全部變爲union併爲整個查詢添加一個排序。或者添加一個人工ID,在這種情況下,這種方式可以很容易地按每個查詢中的不同參數進行排序,但它與接受的答案相同。