从 table 获取多行到另一个 table 的每行

Get multiple rows from a table to per row of another table

我这里有一个问题,我想知道是否可以在一次查询中执行此操作,而不是让服务器执行多次查询。

事情是这样的,我想要的是,在每个类别中,在 24 家商店的限制内搜索属于该类别的所有商店。也就是说,假设我注册了5个类别,我将搜索属于该类别的24家商店,最终我将在查询结果中总共有120家商店。

以下代码是示例,但这只会获取任何类别的前 24 家商店,而不会遍历每个类别。

SELECT *
FROM categories c
    LEFT JOIN (SELECT * FROM stores_categories LIMIT 24 OFFSET 0) sc ON sc.id_category = c.id
WHERE type = 'STORE' OR type = 'ALL';

有人发给我这个,它与我的问题非常相似,How to SELECT the newest four items per category?,有点像,但我希望能够限制并使用偏移量来制作页面,而不仅仅是每个类别中最近的前 24 个。

示例代码来自 link 我得到的:

SELECT sc1.*
FROM stores_categories sc1
    LEFT OUTER JOIN stores_categories sc2 ON (sc1.id_category = sc2.id_category AND sc1.id_store < sc2.id_store)
GROUP BY sc1.id_store
HAVING COUNT(*) < 24
ORDER BY sc1.id_category;

而我的数据库服务器是5.5.64-MariaDB版本。一个 fiddle 示例,可以使用我的数据库中的相同值进行测试。 https://www.db-fiddle.com/f/jcowJL9S4FQXqKg2yMa8kf/0

它可以使用每个类别的计算 row_number

--
-- Emulated row_number via variables
-- 
SELECT sc.id, id_store
, cat.name AS cat_name
, cat.type AS cat_type
, rn
FROM
(
  SELECT sc.*
  , @rn := CASE 
           WHEN @cat_id = sc.id_category
           THEN @rn + 1 ELSE 1
           END AS rn
  , @cat_id := sc.id_category as cat_id
  FROM stores_categories sc
  CROSS JOIN (SELECT @cat_id:=0, @rn:=0) vars
  ORDER BY sc.id_category, sc.id_store DESC, sc.id DESC
) sc
LEFT JOIN categories cat 
  ON cat.id = sc.id_category
WHERE rn BETWEEN 1 AND 24
ORDER BY sc.id_category, sc.id_store DESC, sc.id DESC

--
-- Grouped self-join
-- 
SELECT sc.id, sc.id_store
, cat.name AS cat_name
, cat.type AS cat_type
, COUNT(sc2.id_store) AS cnt
FROM stores_categories sc
LEFT JOIN stores_categories sc2
  ON sc2.id_category = sc.id_category 
 AND sc2.id_store >= sc.id_store
LEFT JOIN categories cat 
  ON cat.id = sc.id_category
GROUP BY sc.id
HAVING cnt BETWEEN 1 AND 24
ORDER BY sc.id_category, sc.id_store DESC;

--
-- Correlated sub-query
-- 
SELECT sc.id, id_store
, cat.name AS cat_name
, cat.type AS cat_type
, ( select count(*)
    from stores_categories sc2
    where sc2.id_category = sc.id_category 
      and sc2.id_store >= sc.id_store
  ) as rn
FROM stores_categories AS sc
LEFT JOIN categories cat 
  ON cat.id = sc.id_category
HAVING rn BETWEEN 1 AND 24
ORDER BY sc.id_category, sc.id_store DESC;

演示 db<>fiddle here