У меня есть следующая таблица в базе данных SQLite3:
CREATE TABLE overlap_results (
neighbors_of_annotation varchar(20),
other_annotation varchar(20),
set1_size INTEGER,
set2_size INTEGER,
jaccard REAL,
p_value REAL,
bh_corrected_p_value REAL,
PRIMARY KEY (neighbors_of_annotation, other_annotation)
);
Я хотел бы выполнить следующий запрос:
SELECT * FROM overlap_results WHERE
(neighbors_of_annotation, other_annotation)
IN (('16070', '8150'), ('16070', '44697'));
Таким образом, у меня есть несколько кортежей идентификаторов аннотации, и я хотел бы выбрать записи для каждого из тех кортежей. Подсказка sqlite3 дает мне следующую ошибку:
SQL error: near ",": syntax error
Как я правильно выражаю это как SQL-оператор?
РЕДАКТИРОВАНИЕ я понимаю, что не объяснил хорошо, что я действительно после. Позвольте мне попробовать другую трещину в этом.
Если человек дает мне произвольный список терминов в neighbors_of_annotation
то, что они интересуются, я могу записать SQL-оператор как следующее:
SELECT * FROM overlap_results WHERE
neighbors_of_annotation
IN (TERM_1, TERM_2, ..., TERM_N);
Но теперь предположите, что человек хочет дать мне пары терминов если форма (TERM_1,1, TERM_1,2)
, (TERM_2,1, TERM_2,2)
, ..., (TERM_N,1, TERM_N,2)
, где TERM_i,1
находится в neighbors_of_annotation
и TERM_i,2
находится в other_annotation
. Язык SQL обеспечивает одинаково изящный способ сформулировать запрос для пар (кортежи) интереса?
Простое решение, кажется, чтобы составить новую таблицу, только для этих пар, и затем присоединиться к той таблице с таблицей, которая будет запрошена и выберет только строки, где первые сроки и вторые сроки соответствуют. Создание тонн AND / OR
операторы выглядят страшными и подверженными ошибкам.
Я никогда не видел такого SQL. Если он существует, я подозреваю, что это нестандартное расширение. Попробуйте:
SELECT * FROM overlap_results
WHERE neighbors_of_annotation = '16070'
AND other_annotation = '8150'
UNION ALL SELECT * FROM overlap_results
WHERE neighbors_of_annotation = '16070'
AND other_annotation = '44697';
Другими словами, создайте динамический запрос из ваших кортежей, но вместо этого как серию объединений или как серию AND внутри OR:
SELECT * FROM overlap_results
WHERE (neighbors_of_annotation = '16070' AND other_annotation = '8150')
OR (neighbors_of_annotation = '16070' AND other_annotation = '44697');
Итак, вместо кода (псевдокод, проверенный только в моем head, поэтому отладка - это ваша ответственность), например:
query = "SELECT * FROM overlap_results"
query += " WHERE (neighbors_of_annotation, other_annotation) IN ("
sep = ""
for element in list:
query += sep + "('" + element.noa + "','" + element.oa + "')"
sep = ","
query += ");"
вместо этого у вас будет что-то вроде:
query = "SELECT * FROM overlap_results "
sep = "WHERE "
for element in list:
query += sep + "(neighbors_of_annotation = '" + element.noa + "'"
query += " AND other_annotation = '" + element.oa + "')"
sep = "OR "
query += ";"
Я не знаю ни одного диалекта SQL, поддерживающего кортежи внутри предложений IN. Я думаю, вы застряли с:
SELECT * FROM overlap_results WHERE (neighbors_of_annotation = '16070' and other_annotation = '8150') or (neighbors_of_annotation = '16070' and other_annotation = '44697')
Конечно, этот конкретный запрос можно упростить до чего-то вроде:
SELECT * FROM overlap_results WHERE neighbors_of_annotation = '16070' and (other_annotation = '8150' or other_annotation = '44697')
Обычно предикаты SQL WHERE-clause позволяют фильтровать только один столбец.