Вот еще один способ сделать это:
1) Использование NOT IN
Вы добавляете условие на usertable.user_id
, которое не должно быть всписок идентификаторов: все эти идентификаторы являются идентификаторами таблицы friendrequests
и friends
, которые имеют to_id
или from_id
= 100.
SELECT
usertable.name,
usertable.user_id,
usertable.image
FROM `UserTable` AS usertable
WHERE usertable.user_id <> '100'
AND usertable.user_id NOT IN
(SELECT from_id as user_id FROM friendrequests WHERE to_id = '100'
UNION
SELECT to_id as user_id FROM friendrequests WHERE from_id = '100'
UNION
SELECT from_id as user_id FROM friends WHERE to_id = '100'
UNION
SELECT to_id as user_id FROM friends WHERE from_id = '100')
ORDER BY usertable.joining_date DESC
LIMIT 10
РЕДАКТИРОВАТЬ в соответствиина комментарий Рика Джеймса, то же самое без объединения:
SELECT
usertable.name,
usertable.user_id,
usertable.image
FROM `UserTable` AS usertable
WHERE usertable.user_id <> '100'
AND usertable.user_id NOT IN (SELECT from_id as user_id FROM friendrequests WHERE to_id = '100')
AND usertable.user_id NOT IN (SELECT to_id as user_id FROM friendrequests WHERE from_id = '100')
AND usertable.user_id NOT IN (SELECT from_id as user_id FROM friends WHERE to_id = '100')
AND usertable.user_id NOT IN (SELECT to_id as user_id FROM friends WHERE from_id = '100')
ORDER BY usertable.joining_date DESC
LIMIT 10
2) Используя LEFT JOIN
Я видел этот ответ и пыталсяиспользовать ту же логику: вы создаете LEFT JOIN
с другой таблицей и добавляете условие, при котором эти объединения возвращают значение NULL
SELECT
usertable.name,
usertable.user_id,
usertable.image
FROM `UserTable` AS usertable
LEFT JOIN friendrequests as FRa on FRa.from_id = usertable_user_id
LEFT JOIN friendrequests as FRb on FRb.to_id = usertable_user_id
LEFT JOIN friends as Fa on Fa.from_id = usertable_user_id
LEFT JOIN friends as Fb on Fb.to_id = usertable_user_id
WHERE usertable.user_id <> '100'
AND FRa.from_id IS NULL
AND FRb.to_id IS NULL
AND Fa.from_id IS NULL
AND Fb.to_id IS NULL
3) Использование NOT EXISTS
SELECT
usertable.name,
usertable.user_id,
usertable.image
FROM `UserTable` AS usertable
WHERE usertable.user_id <> '100'
AND NOT EXISTS (SELECT from_id as user_id FROM friendrequests WHERE to_id = '100')
AND NOT EXISTS (SELECT to_id as user_id FROM friendrequests WHERE from_id = '100')
AND NOT EXISTS (SELECT from_id as user_id FROM friends WHERE to_id = '100')
AND NOT EXISTS (SELECT to_id as user_id FROM friends WHERE from_id = '100')
ORDER BY usertable.joining_date DESC
LIMIT 10
Извините, но без примеров данных или SQL Fiddle для проверки этого запроса, я не могу сказать вам, вернет ли он то, что вы хотите, или он действительно быстрее ...
РЕДАКТИРОВАТЬ : Эта страница с 2009 года, поэтому с тех пор результат изменился!Я не буду стирать его, поскольку у вас все еще есть структура запросов, которую я использовал ранее:
Я рекомендую вам просмотреть эту страницу, чтобы понять разницу между этими запросами и дать вам представление о том, чего вы хотите: https://explainextended.com/2009/09/18/not-in-vs-not-exists-vs-left-join-is-null-mysql/
На этой странице предлагается третий способ (с использованием NOT EXISTS
), но согласно тесту он неэффективен:
Этот запрос, однако, немного менее эффективенпо сравнению с предыдущими двумя: это занимает 0,92 с.
Это не очень значительное снижение производительности, однако запрос занимает на 27% больше времени.