#mysql #sql
Вопрос:
У меня есть два стола, activity
и users
. Я пытаюсь извлечь данные, используя несколько предложений where.
SELECT SUM(activity.step_points) AS s_points
, `activity`.`user_id`
, `users`.`id`
, `users`.`app_id`
, `users`.`country_id`
FROM `activity`
LEFT JOIN `users` ON `users`.`id` = `activity`.`user_id`
WHERE `users`.`is_active` = 1 AND
`users`.`is_test_account` = 0 AND
`users`.`app_id` = 3 AND
`users`.`country_id` = 1 AND
`users`.`phone` NOT LIKE "0000%" OR
`users`.`phone` IS NULL AND
`users`.`is_subscribed` = 1 AND
(`users`.`email` NOT LIKE "%@mycompanyname.net" OR
`users`.`email` IS NULL) AND
YEAR(`activity`.`created_at`) = "2021" AND
MONTH(`activity`.`created_at`) = "06"
GROUP BY `activity`.`user_id`
ORDER BY `s_points` DESC LIMIT 100 OFFSET 0
Но я думаю users.country_id = 1
, что этим пренебрегают. Вы можете видеть, что мне нужны только строки, относящиеся к идентификатору страны 1. Но я тоже получаю идентификатор страны 2, 3.
Почему это происходит?
Комментарии:
1. Вам нужно быть осторожным, когда у вас есть сочетание предложений » И » с » ИЛИ «где». Попробуйте использовать скобки, чтобы убедиться, что они правильно интерпретированы.
2. @Найджелрен так правдив
3.
so true
Означает ли это, что ваша проблема теперь решена?4. @JamesZ да, это решило мою проблему
5.
LEFT JOIN x... WHERE x =...
это то же самое, чтоINNER JOIN x...
Ответ №1:
Вам нужно правильно использовать круглые скобки в WHERE
предложении, чтобы OR
не доминировать над AND
s:
SELECT . . .
FROM activity a JOIN
users u
ON u.id = a.id
WHERE u.is_active = 1 AND
u.is_test_account = 0 AND
u.app_id = 3 AND
u.country_id = 1 AND
(u.phone NOT LIKE '0000%' OR u.phone IS NULL) AND
u.is_subscribed = 1 AND
(u.email NOT LIKE '%@mycompanyname.net OR u.email IS NULL) AND
(a.created_at >= '2021-01-01' AND a.created_at < '2022-01-01'
Обратите внимание на другие изменения в коде:
- Вы выполняете фильтрацию по обеим таблицам, поэтому внешнее соединение не подходит.
WHERE
Предложение все равно превращает его во внутреннее соединение. - Псевдонимы таблиц облегчают написание и чтение кода.
- Все обратные ссылки просто усложняют написание и чтение кода и не нужны.
- Стандартный разделитель SQL для строк-одинарные кавычки. Используйте их, если у вас нет веских причин для предпочтения двойных кавычек.
- Для сравнения дат может быть быстрее избежать функций, отсюда и изменение для сравнения за год. Это помогает оптимизатору.