Выборка записей из many-to-many таблицы (PostgreSQL)
Коллеги, дайте ума, пожалуйста. Проще всего будет объяснить на примере "повареной книги". Есть рецепты и есть ингредиенты. Many-to-many табличка выглядит примерно так:
-------------------------
| recipes_ingredients |
-------------------------
recipe_id | ingredient_id
-------------------------
r_id_1 | i_id_1
r_id_1 | i_id_2
r_id_2 | i_id_3
r_id_2 | i_id_2
r_id_2 | i_id_4
r_id_3 | i_id_1
r_id_3 | i_id_2
Пользователь хочет выбрать все рецепты, которые содержат только ингредиенты i_id_1
И i_id_2
. Эти продукты могут содержаться и в других рецептах, но поскольку в этих других рецептах содержатся и другие продукты, которых у пользователя нет, то в результат должны попасть 2 рецепта с r_id_1
и r_id_3
. Я пробовал выборки с any и all, вроде такой:
select * from recipes_ingredients
where ingredient_id = any('{i_id_1, i_id_2}');
но очевидно, что в таком варианте выбирается И рецепт с r_id_2
.
Пытался как-то подзапросами решить, но стало очевидно, что знаний и опыта не хватает, да и пример запроса по памяти уже не приведу. В общем, буду благодарен за вашу помощь!
Ответы (1 шт):
Обычное логическое деление. В общем случае можно как-то так:
SELECT recipe_id
FROM recipes_ingredients
GROUP BY recipe_id
HAVING SUM((ingredient_id IN ( i_id_1, i_id_2 )) :: INT ) = 2
AND SUM((ingredient_id NOT IN ( i_id_1, i_id_2 )) :: INT ) = 0