MySQL: как массивы SELECT строк с несколькими парами в предложении WHERE
Скажем, у меня есть таблица email_phone_notes
, которая выглядит так:
+-----------------------+--------------+------+-----+---------+-------+
| Field | Type | Null | Key | Default | Extra |
+-----------------------+--------------+------+-----+---------+-------+
| email | varchar | NO | PRI | NULL | |
| phone | varchar | NO | PRI | NULL | |
| notes | text | NO | | 0 | |
+-----------------------+--------------+------+-----+---------+-------+
Таким образом, каждая комбинация электронной почты и телефона уникальна, но у вас может быть несколько адресов электронной почты с разными номерами телефонов и наоборот. Это немного надуманно, но это отражает мой сценарий.
Я хотел бы сделать такой запрос:
SELECT * FROM email_phone_notes WHERE email = '[email protected]' AND phone = '555-1212';
Но я бы хотел сделать несколько пар одновременно, поэтому мне не нужно делать несколько запросов SELECT
. Также важно сохранить пары вместе, потому что я не хочу возвращать ошибочную комбинацию телефона/электронной почты, которая не запрашивалась.
Я мог бы сделать что-то подобное, но для возможности нескольких сотен значений запрос будет очень длинным.
SELECT * FROM email_phone_notes WHERE (
(email='[email protected]' && phone='555-1212') ||
(email='[email protected]' && phone='888-1212') ||
...
Есть ли более элегантное решение, или я должен придерживаться этого? Спасибо!
Ответы
Ответ 1
Если вы после элегантного SQL, вы можете использовать конструкторы строк:
SELECT * FROM email_phone_notes WHERE (email, phone) IN (
('[email protected]' , '555-1212'),
('[email protected]', '888-1212')
-- etc.
);
Тем не менее, это вовсе не удобно для индексирования и не рекомендуется для таблицы любого значительного размера. Вместо этого вы можете материализовать таблицу с вашими желаемыми парами и присоединиться к ней со своей таблицей:
SELECT * FROM email_phone_notes NATURAL JOIN (
SELECT '[email protected]' AS email, '555-1212' AS phone
UNION ALL
SELECT '[email protected]', '888-1212'
-- etc.
) t;
Или еще предварительно заполнить (временную) таблицу:
CREATE TEMPORARY TABLE foo (PRIMARY KEY (email, phone)) Engine=MEMORY
SELECT email, phone FROM email_phone_notes WHERE FALSE
;
INSERT INTO foo
(email, phone)
VALUES
('[email protected]' , '555-1212'),
('[email protected]', '888-1212')
-- etc.
;
SELECT * FROM email_phone_notes NATURAL JOIN foo;
Ответ 2
Вы можете использовать конструктор строк следующим образом:
SELECT *
FROM email_phone_notes
WHERE (email, phone) IN (
('[email protected]', '555-1212'),
('[email protected]', '888-1212')
)
Пример SQLfiddle