[英]MySQL - Selecting rows based on conditions
如果mem_id
表中不存在swipes
,我有一個查詢從members
表中選擇用戶。 查詢如下:
SELECT members.* FROM members
WHERE NOT EXISTS (SELECT * FROM swipes WHERE (mem_id IN (swp_by, swp_to) AND :mem IN (swp_by)))
上面的查詢完成了我一半的工作。 但是,我想在這里添加更多條件。 在swipes
表中,有兩個字段,即swp_type
和swp_status
。 這里swp_type
有ENUM
值left, right, top
顯示刷卡是 left, right 或 top(如 tinder), swp_status
也有ENUM
值requested, accepted, declined, unmatched
,表示請求的朋友是否仍在請求 state,或被接受,或被拒絕,或在接受不匹配之后。 現在我想修改上面的查詢,使其在條件中接受這兩個表並根據它們返回結果。
讓我們舉個例子:
假設有兩個用戶 1 和 2。現在swipes
表中沒有記錄,因此用戶 1 和 2 可以看到彼此。
現在,假設用戶 1 向左刷了用戶 2,那么:
swp_by: 1, swp_to: 2, swp_type: left, swp_status: requested
對於上述數據,用戶 1 向左滑動了用戶 2(這意味着用戶 1 不想與用戶 2 匹配),因此他們將無法再看到對方。
現在,假設用戶 1 RIGHT 或 TOP 刷了用戶 2,那么:
swp_by: 1, swp_to: 2, swp_type: right/top, swp_status: requested
對於上述數據,用戶 1 看不到用戶 2,但用戶 2 可以看到用戶 1,因為這里的swp_type
是正確的,並且swp_status
是requested
的。
現在說,對於上述數據swp_status
沒有被requested
,但除了requested
之外的任何其他內容都說(接受/拒絕),那么兩個用戶將無法再看到對方。 這是我想作為條件添加到當前查詢中的內容。
考慮到swp_by
和swp_to
,我當前的查詢通過顯示swipes
表中不存在的成員來完成一半的工作。 如上所述,我想添加swp_type
和swp_status
的條件。
我試過什么?
我嘗試了以下方法,但最終給出了奇怪的結果。 它返回了所有成員,根據數據它應該只返回mem_id
8
的成員,因為它不存在於與用戶 1 和用戶12
相關的滑動表中,因為它是right
和requested
的,而用戶15
是top
和requested
的.
SELECT * FROM members
WHERE NOT EXISTS (SELECT * FROM swipes WHERE (mem_id IN (swp_by, swp_to) AND 1 IN (swp_by)) AND swp_type != 'left' AND swp_status = 'requested')
因此,我認為這不是我必須設置條件的方式。
小提琴在這里: DB FIDDLE
我要在這里冒險,因為我承認我很難聽從你的解釋。 最后,我不知道您是在描述信用卡處理、約會服務還是其他東西。 因此,您可能必須根據我可能存在的任何誤解來“調整” SQL。
為了更好地理解我的 SQL,我取了你原來的 SQL:
SELECT members.* FROM members
WHERE NOT EXISTS (SELECT * FROM swipes WHERE (mem_id IN (swp_by, swp_to) AND 1 IN (swp_by)))
並將其重鑄為我認為是等價的並將其用作起點:
SELECT members.* FROM members
WHERE mem_id <> 1
AND NOT EXISTS (
SELECT * FROM swipes WHERE mem_id = swp_to AND swp_by = 1
)
我最終得到:
SELECT * from members
WHERE mem_id <> 1
AND NOT EXISTS (
SELECT * FROM swipes WHERE
members.mem_id = swp_by and 1 = swp_to OR
members.mem_id = swp_to and 1 = swp_by
)
UNION
SELECT * FROM members
WHERE mem_id <> 1
AND EXISTS (
SELECT * FROM swipes WHERE swp_by = members.mem_id AND swp_to = 1
AND swp_type <> 'left' AND swp_status = 'requested'
)
這是一個工會。 第一段是:
SELECT * from members
WHERE mem_id <> 1
AND NOT EXISTS (
SELECT * FROM swipes WHERE
members.mem_id = swp_by and 1 = swp_to OR
members.mem_id = swp_to and 1 = swp_by
)
這是試圖 select 所有“與用戶 1 相關的滑動表中不存在”的行,這將與您的示例數據mem_id 8
一起使用。 現在也許它應該只檢查swp_by=1
和swp_to=8
而不是swp_by=8
和swp_to=1
(反之亦然)。 如果是這樣,您可以進行調整。
聯合的第二部分添加具有相應滑動( swp_by
設置為mem_id
)且swp_type
不等於'left'
和swp_status
等於'requested'
且swp_to
等於1
的行。 我根據您的示例數據和您說您期望返回的行使用了這個標准:
SELECT * FROM members
WHERE mem_id <> 1
AND EXISTS (
SELECT * FROM swipes WHERE swp_by = members.mem_id AND swp_to = 1
AND swp_type <> 'left' AND swp_status = 'requested'
)
如果 SQL 不是您所需要的,我認為只需要稍作調整即可。
以上也可以使用內連接和外連接來完成:
SELECT members.* from members LEFT JOIN swipes ON
mem_id = swp_by AND 1 = swp_to OR
mem_id = swp_to and 1 = swp_by
WHERE mem_id <> 1 AND swp_id is NULL
UNION
SELECT DISTINCT members.* FROM members JOIN swipes ON
mem_id = swp_by AND
swp_to = 1 AND
swp_type <> 'left' AND
swp_status = 'requested'
WHERE mem_id <> 1
看上面的建議,有機會移除工會:
SELECT DISTINCT members.* from members LEFT JOIN swipes ON
mem_id = swp_by AND 1 = swp_to OR
mem_id = swp_to AND 1 = swp_by
WHERE mem_id <> 1 AND
swp_id is NULL OR (
mem_id = swp_by AND
swp_to = 1 AND
swp_type <> 'left' AND
swp_status = 'requested'
)
ORDER BY mem_id
聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.