Допустим, у меня есть эта таблица:Найти вхождения отмеченных элементов в таблице тузд
item_id tag_id
------- ------
1 1
1 2
2 2
2 3
Как вы можете себе представить, это таблица, в которой у меня есть ссылки на некоторые предметы и теги, которые принадлежат им. Элемент может иметь более одного тега, и один тег можно выбрать для нескольких элементов.
Предположим, у меня есть также специальный коллектив тегов (f.ex. tag_id = 50, 73 и 119) и таблица «items» с идентификатором (указанным item_id
).
Есть ли эффективный запрос, который дает мне:
- количество элементов с этими тегами
- сами пункты?
То, что я пытался
SELECT COUNT(*) FROM
(
SELECT COUNT(*) AS c FROM items_tags it JOIN items i ON i.id = it.item_id
WHERE (tag_id=7 OR tag_id=95 OR tag_id=150) AND `status`='active'
GROUP BY item_id
) t1 WHERE c=3 <-- c= number of tags
я могу иметь оба результата, но с очень (кажется) неэффективный запрос. После экзамена с EXPLAIN я хотел бы избавиться от «диапазона», данного OR.
Уточнение моей проблемы: Проблема в том, что мне была дана очень плохо написанная PHP-фреймворк, которая повторяется более 900 раз через различные идентификаторы тегов. Предположим, у вас есть один или несколько фиксированных идентификаторов (выбранные теги), и он повторяет все теги 900+, чтобы найти количество вхождений элементов, которые имеют общие теги PLUS, итерацию (это функция для уточнения поиск, показывающий только те элементы, у которых есть все теги плюс один).
Данный код работает следующим образом: я выбираю один или несколько тегов и их идентификатор входят в строку запроса. Предположим, я выбрал теги 54 и 77. Код должен найти каждый элемент ID для элементов, которые имеют BOTH теги 54 и 77, и перечислить их один за другим: мы получаем список «элементы с выбранными тегами».
Затем он предлагает выбор для уточнения поиска, и здесь идет нечетная часть: цикл кода PHP обрабатывает ВСЕ теги 900+, и для каждой итерации он принимает тег и подсчитывает, сколько элементов имеет ВСЕ теги 54, 77 и один на итерации. Если счетчик> 0, он отображает имя тега с номером счета, отфильтровывая каждый тег, элементы которого не имеют ссылки на выбранные теги.
Было бы неплохо добиться такого же результата в менее интенсивном режиме.
Какой результат вы ожидаете? –
Вам нужны элементы, которые соответствуют _all_ те теги или _any_ из них? – PinnyM
Все они, спасибо. Вывод, который я ожидаю, в первом случае представляет собой одно число элементов, соответствующих всем тегам, во втором - строки таблицы «items» с совпадением идентификатора item_id, имеющего все теги. – Cranio