2013-02-22 82 views
1

所以我有一個表,my_table有一個主鍵,idINT),並進一步列fooVARCHAR)和barDOUBLE)。每foo應出現一次在我的表中,與相關bar值,但我知道我有幾個行與foo相同不同bar s。如何獲得包含相同foo值但具有不同bar s(例如,相差超過10)的那些行的列表? 我想:MySQL表自連接返回的行數太多

 
    SELECT t1.id, t1.bar, t2.id, t2.bar, t1.foo 
    FROM my_table t1, my_table t2 
    WHERE t1.foo=t2.foo 
    AND t1.bar - t2.bar > 10.; 

,但我得到很多很多的結果(比中行my_table的總數還多)。我覺得我一定在做一些非常明顯的愚蠢行爲,但是看不到我的錯誤。

啊 - 謝謝SWeko:我想我明白爲什麼我會得到如此多的結果。有沒有計算SQL的方法,對於每個foofoobar之間的差值大於10的行數。

+0

相差10 t1.bar - t2.bar = 10 – 2013-02-22 15:43:26

+0

我想他的意思相差至少10 – 2013-02-22 15:44:01

回答

0

如果,例如,你有5列foo='A'和10行與foo='B'自聯接將加入每一個行與對方行(包括其本身),並且每個B-行彼此B-行,所以一個簡單的

SELECT t1.id, t1.bar, t2.id, t2.bar, t1.foo 
FROM my_table t1, my_table t2 
WHERE t1.foo=t2.foo 

將返回5*5+10*10=125行。過濾值會削減該數字,但您可能仍然有(顯着)多於您開始使用的行數。例如。如果我們假設在B行有5 bar通過50分別值,這將意味着他們將匹配有:

bar = 5 - 0 rows that have bar less than -5 
bar = 10 - 0 rows that have bar less than 0 
bar = 15 - 0 rows that have bar less than 5 
bar = 20 - 1 rows that have bar less than 10 
bar = 25 - 2 rows that have bar less than 15 
bar = 30 - 3 rows that have bar less than 20 
bar = 35 - 4 rows that have bar less than 25 
bar = 40 - 5 rows that have bar less than 30 
bar = 45 - 6 rows that have bar less than 35 
bar = 50 - 7 rows that have bar less than 40 

所以你將有28個成績爲B-行獨自一人,那數字隨着具有相同值foo的行的平方上升。

-1

您是否嘗試過使用「新」JOIN語法的相同內容?

SELECT t1.*, 
      t2.* 
     FROM my_table t1 
     JOIN my_table t2 ON t1.foo = t2.foo 
    WHERE (t1.bar - t2.bar) > 10 

我不懷疑這會解決你的問題,但對我來說,至少在哪裏我會開始。

我也可以試試這個:

SELECT t1.*, 
      t2.* 
     FROM my_table t1 
     JOIN my_table t2 ON t1.foo = t2.foo AND t1.id != t2.id 
    WHERE (t1.bar - t2.bar) > 10 
+0

這是首選,但它顯然不是問題,因爲它完全等同於OP的查詢。 – 2013-02-22 15:46:24

+0

-1添加的查詢沒有意義。一行永遠不會加入自己,因爲您已經要求匹配的行具有不同的bar值。只是「嘗試」隨機的東西並希望問題消失是不好的。你必須真正弄清楚並修復它! – 2013-02-22 15:52:09

+0

你爲什麼恨我,dan1111? – 2013-02-22 16:04:34

2

要回答你的問題的最新:

是否有票的SQL的方式,爲每個FOO,行 與富,但酒吧超過10不同的是多少?

這樣的查詢應該工作:

select t1.id, t1.foo, t1.bar, count(t2.id) as dupes 
from my_table t1 
    left outer join my_table t2 on t1.foo=t2.foo and (t1.bar - t2.bar) > 10 
group by t1.id, t1.foo, t1.bar;