2011-02-05 94 views
1

有一個MySQL數據庫看起來像這樣:SQL選擇最近的記錄如何限制一列

ID /名稱/愛好/省/創建 - INT8

我想選擇只有三個記錄每一個省,但我不知道如何...

所以結果應該看起來像這樣

[province1]

[1]等等喇嘛

[2]等等等等

[3]等等等等

[province2]

[1]嗒嗒BLA

[2]等等等等

[3]等等等等

感謝您的幫助。 此致敬禮。 M.

回答

1
SELECT * FROM 
(
    SELECT t1.*, @num := IF(@t1 = province,@num+1,1) as num_in_group, @t1 := province 
    FROM table_name t1 
    INNER JOIN (SELECT @num:=0) num_table 
    ORDER BY province ASC, id desc 
)xxx WHERE num_in_group <=3 

這是相當簡單的,而不是方法很有效,但它可能是有益的,一個好的開始。

UPDATE

SELECT * FROM 
(
    SELECT t1.*, @num := IF(@t1 = province,@num+1,1) as num_in_group, @t1 := province 
    FROM table_name t1 
    INNER JOIN (SELECT @num:=0) num_table 
    INNER JOIN (SELECT @t1 := NULL)x1 
    ORDER BY province ASC, id desc 
)xxx WHERE num_in_group <=3 
+0

首先 - 感謝您的幫助。上面的腳本工作得很好,但是我對所有結果都有num_table = 1。但結果很好排序。 – Pablo 2011-02-05 22:15:36

1

我不認爲這可以通過一個查詢來完成,除非您的數據庫很小,因此您可以在腳本中進一步過濾。

  • 首先,找出你有什麼省份:SELECT DISTINCT省FROM t請求
  • 運行由「創建DESC」每個省的一個單獨的查詢,排序,並限3
  • 確保「省「和」創建「都被編入索引。
+0

在一個循環做查詢始終是一個壞的解決方案。 – 2011-02-05 22:02:47

+1

可以在1個查詢中完成 – a1ex07 2011-02-05 22:07:41

0

這不會對MySQL的工作(這就是爲什麼我畫這個答案爲社區維基),但它使用不同的數據庫管理系統,並就這個問題絆人很有趣:

WITH TT (id, province, R) AS (
    SELECT id, province, row_number() OVER(PARTITION BY province ORDER BY id DESC) 
     FROM your_table 
    GROUP BY id, province 
) 
SELECT id, province 
    FROM TT 
WHERE R <= 3; 
1

在支持row_number()的數據庫中,「每組最多N個」問題非常容易,但MySQL不是其中之一。據我所知,只有相當醜陋的解決方法。一種方法是group_concat方式:

select yt.province 
,  lst.value 
,  substring_index(
      substring_index(
       group_concat(name separator ';'), 
       ';',lst.value), 
      ';',-1) 
from YourTable yt 
cross join 
     (
     select 1 as value 
     union all select 2 
     union all select 3 
     ) lst 
group by 
    yt.Province 
,  lst.value; 

這將返回重複的行,如果有低於每省三個名字。你可以用另一個子查詢排除這些。

另一種方法是變量的方式,由亞歷克斯(我投票)發佈。在一個稍微不同的格式:

select * 
from (
     SELECT name 
     ,  province 
     ,  @num := if(@lastprov = province,@num+1,1) as num_in_group 
     ,  @lastprov := province 
     from YourTable yt 
     order by 
       province 
     ) as SubQueryAlias 
JOIN (SELECT @num:=0, @lastprov:=null) as DeclareVariablesSubquery 
WHERE num_in_group <= 3; 

測試數據:

drop table if exists YourTable; 

create table YourTable (id int, name varchar(25), province varchar(25)); 
insert YourTable values 
    (1,'Barack','New York'), 
    (2,'George W','New York'), 
    (3,'William','New York'), 
    (4,'George HW','New York'), 
    (5,'Ronald','Texas'), 
    (6,'James','Texas'), 
    (7,'Gerald','Texas'), 
    (8,'Richard','Texas'), 
    (9,'Lyndon','California'), 
    (10,'John','California'), 
    (11,'Dwight','Rhode Island'), 
    (12,'Harry','Wisconsin');