[英]My SQL Query to get Mutual/Friends Followers
我有一張像下面的桌子:
id | Follower_id | leader_id | status
----------------------------------------
1 | 2 | 1 | approved
2 | 1 | 2 | approved
3 | 3 | 2 | approved
4 | 1 | 3 | approved
從此表中,我要檢索相互的Follower_id / leader_id。
對於示例2,此表中的1是相互的。 為此,我正在使用以下sql
SELECT r.follower_id RF
, r.leader_id RL
, l.follower_id LF
, l.leader_id LL
FROM followers r
JOIN followers l
ON l.follower_id = r.leader_id
AND l.leader_id = r.follower_id
WHERE r.status = 'approved'
AND l.status = 'approved';
它返回預期的輸出,但是非常慢。
如何優化此SQL?
也許更簡單的方法可能會更快地工作,例如
SELECT follower_id, leader_id
FROM followers a
WHERE follower_id IN (
SELECT follower_id
FROM followers b
WHERE a.leader_id = b.leader_id
AND status = 'approved'
)
AND status = 'approved';
您正在將整個表與同一張表連接在一起。 那沒有道理。 嘗試“內部加入”,這樣在領導者擁有相同追隨者或跟隨者具有相同領導者的情況下,您將獲得收益。 另外,您還需要使用別名as
聯接表的方式。
SELECT *
FROM followers as f
INNER JOIN followers as k on f.follower_id = k.leader_id
WHERE f.follower_id like k.leader_id OR f.follower_id = k.leader_id
在某人大驚小怪之前,這是一個示例腳本,向您顯示了bouth表的所有條目。 在這種情況下,兩次相同的表。
更好的方法是制作2個表。 創建一個記帳表和一個跟隨表並將它們聯接。 應該工作得很好並且更快。
如果要使用更多方法來連接表,請在此處查看: https : //www.w3schools.com/sql/sql_join.asp
您的查詢產生重復的記錄。 這也會給您的mysql連接造成一些延遲。
避免重復就是解決您的問題。
我在下面添加我的作品,
SELECT r.follower_id RF
, r.leader_id RL
, l.follower_id LF
, l.leader_id LL
FROM sample r
JOIN sample l
ON l.follower_id = r.leader_id
AND l.leader_id = r.follower_id AND r.id < l.id
WHERE r.status = 'approved'
AND l.status = 'approved';
輸出:
RF RL LF LL
2 1 1 2
注意:請使用您的table name
代替sample
。
有時EXISTS非常有效:
select
t.follower_id id1,
t.leader_id id2
from followers t
where
status = 'approved'
and
t.follower_id < t.leader_id
and
exists (
select 1 from followers
where status = 'approved' and follower_id = t.leader_id and leader_id = t.follower_id
)
該查詢將僅返回每對一次。
參見演示 。
結果:
| id1 | id2 |
| --- | --- |
| 1 | 2 |
首先,您可以使用索引優化此查詢:
SELECT r.follower_id as RF, r.leader_id as RL,
l.follower_id as LF, l.leader_id as LL
FROM followers r JOIN
followers l
ON l.follower_id = r.leader_id AND
l.leader_id = r.follower_id
WHERE r.status = 'approved' AND l.status = 'approved';
以下索引應該有所幫助: followers(follower_id, leader_id, status)
。
我寧願將其寫為exists
。 您也可以嘗試聚合:
SELECT f.follower_id, f.leader_id
FROM followers f
WHERE f.status = 'approved'
GROUP BY LEAST(f.follower_id, f.leader_id),
GREATEST(f.follower_id, f.leader_id)
HAVING MIN(f.follower_id) = MIN(f.leader_id);
最后一個條件保證您在數據中具有兩個方向。
聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.