помогите составить запрос: выборка из 2 таблиц

Demona

Новичок
Есть две таблицы
1. table_1 - информация о товарах:
item_id (auto_increment, uniq)
--

1
2
3
4
5
5

2. table_2 информация о категориях этого товарах
item_id
cat_id
---
1 | 3
1 | 4
2 | 1
3 | 1
1 | 1
4 | 2
5 | 2
2 | 3

Задача выбрать товар содержащий определенные категории. К примеру по запросу cat_id = 3 AND cat_id = 4 должен вывестись товар 1.

Думаю вопрос простой, но я так и не могу до конца разобраться со всем синтаксисом mysql :(

Спасибо!

SELECT table_1.item_id FROM table_1 LEFT JOIN table_2 ON table_1.item_id = table_2.item_id WHERE ( table_2.cat_id = 1 ) AND( table_2.cat_id = 23 ) AND( table_2.cat_id = 9 )
 

Фанат

oncle terrible
Команда форума
Во-первых, надо убрать лефт джойн. тебе нужны только те записи в т2, которым есть соответствия в т1
Во-вторых, надо использовать самим же собой назначенные имена полей. если имя поля - item_id, то его и надо писать, а не entry_id
В-третьих, вместо колбасы из AND-ов, надо писать IN:

PHP:
WHERE table_2.cat_id IN ( 1,3,5 );
в остальном запрос навскидку верный, запускай и пиши конкретные ошибки если будут

И вообще, учись писать нормальные вопросы. Не "вот вам код перепишите его за меня", а подробно описывать, что происходит - какие ошибки, какой результат
 

Demona

Новичок
Спасибо за ответ!
а ошибок не было - просто 0 результатов (я случайно удалила строчку-комментарий по этому поводу). Запрос на самом деле правильный - в реальной базе используется entry_id - item_id я написала для упрощения понимания. По поводу IN - мне нужно выбрать товары которые содержать все категори по условию - по принципу AND . А IN работает, но выводит по принципу ИЛИ :(
 

Фанат

oncle terrible
Команда форума
ну раз ноль результатов - убираем постепенно условия, потом добавляем.
но начала убеждаемся в том, что ошибки, если они есть запросе, будут выведены программисту.
допустим, вместо SELECT пишем ELECT
если всё так же 0 вариантов - сначала учимся выводить ошибки и исправляем их.
 

Фанат

oncle terrible
Команда форума
но вообще, конечно, самое главное - это запрос, реально соответствующий условиям задачи.
а не высосанные из пальца случайным образом составленные куски кода и данных.

к примеру, в запросе присутствует table_2.cat_id = 9
согласно приведённым данным, запрос и не должен ничего возвращать.

если не можешь нормально написать вопрос, то не нужно тратить ни своё, ни чужое время.
 

Demona

Новичок
синтаксические ошибки у меня отладчик выводит. Поэтому это не проблема. Я думаю, что понимаю почему не получается - mysql пытается выбрать значения в котором на уровне одной row cat_id = 3 и 4. Что есть ошибка, т.к. на уровне одной линии это не возможно.

вот последний вариант моего запроса (результат выборки - 0)
SELECT table_1.item_id FROM table_1 as ct JOIN table_2 as cp ON ct.item_id = cp.item_id WHERE cp.cat_id = 3 AND cp.cat_id = 4
 

Demona

Новичок
запросы выполняются через библиотеку codeigniter'a, поэтому тест ELECЕ дает:
You have an error in your SQL syntax; check the manual that corresponds to your MySQL server version for the right syntax to use near

- а это откуда? Я привела пример ровно по тем данным примера в хедере.
 

Фанат

oncle terrible
Команда форума
mysql пытается выбрать значения в котором на уровне одной row cat_id = 3 и 4. Что есть ошибка, т.к. на уровне одной линии это не возможно.
верно.
поэтому надо сделать из двух строк - одну.
для этого обычно используется ещё один джойн.
то есть, если нам надо сделать выборку по одной категории, то делаем джойн таблицы товаров с категориями по кат айди. А если надо добавить ещё одну категорию к выборке, то делаем ещё один джойн таблицы категорий, со вторым cat_id.
таким образом мы получим новую таблицу, в которой строки будут составлены из двух строк, составленных по условию AND.
 

chira

Новичок
в приведённом решении количество джоинов будет равно количеству проверяемых категорий
возможно обойтись одним джоином:
select ct.*
from table_1 ct
where exists (select null from table_2 cp where ct.entry_id=cp.entry_id and cp.cat_id in (3,4) having count(distinct cp.cat_id)=2)

если нужно будет сравнить три категории, к примеру 1,3,4
... cp.cat_id in (1,3,4) having count(distinct cp.cat_id)=3
 
Сверху