【问题标题】:SQL select all products from specified category and all sub-categorySQL从指定类别和所有子类别中选择所有产品
【发布时间】:2020-04-28 17:24:54
【问题描述】:

项目表

id    category_id    item_title
1     2              Seagate SSHD
2     3              Seagtate 2.5 inch HDD
3     4              Western Digital 3.5 inch HDD
4     4              Toshiba 3.5 inch HDD
5     5              Generic Used Monitor
6     6              ASUS Monitor

分类表

id    parent_id    category_title
1     0            Hardware
2     1            Hard Disks
3     2            Laptop Hard Disk
4     2            Desktop Hard Disk
5     1            Monitor
6     5            LCD Monitor

视觉:

                         -- Laptop Hard Disk
          -- Hard Disks |
 Harware-|               -- Desktop Hard Disk
          -- Monitors    -- LCD Monitor

查询:

SELECT * FROM items_table p
JOIN categories_table cp ON p.category_id = cp.id
JOIN categories_table cc ON cp.parent_id = cc.id
WHERE cc.id = "1"

输出

id    category_id    item_title
1     2              Seagate SSHD
5     5              Generic Used Monitor

但是, 我也在尝试从所有子类别中获取项目, IE; 1.请求父类时必须显示父类、子类和孙子类的所有内容 2.当请求子类别时,必须显示子及其子(孙子)的所有内容

期待; 当请求类别 1(硬件)时

id    category_id    item_title
1     2              Seagate SSHD
2     3              Seagtate 2.5 inch HDD
3     4              Western Digital 3.5 inch HDD
4     4              Toshiba 3.5 inch HDD
5     5              Generic Used Monitor
6     6              ASUS Monitor

当请求类别 2(硬盘)时

id    category_id    item_title
1     2              Seagate SSHD
2     3              Seagtate 2.5 inch HDD
3     4              Western Digital 3.5 inch HDD
4     4              Toshiba 3.5 inch HDD

如何修改我的查询以获取类别中的所有项目及其所有子类别?

【问题讨论】:

  • 你用的是什么版本的mysql?
  • mysql 5.7.24 和 v10.1 MariaDB

标签: mysql parent-child hierarchy hierarchical-data


【解决方案1】:

我必须警告id-parentId 方法(称为邻接列表)不适用于任意级别的嵌套。但是,如果您知道它只是 3 层,那就顺其自然吧。否则,请查看嵌套集或物化路径等替代方案。

解决方案是从所有 3 级类别中获取所有需要的类别 ID,然后将它们应用到 items 表。

SELECT *
FROM items
WHERE category_id IN (
  SELECT :cat_id AS id
    UNION ALL
  SELECT c2.id FROM categories AS c2 
  WHERE c2.parent_id = :cat_id
    UNION ALL
  SELECT c3.id FROM categories AS c3 
  JOIN categories AS c3p ON c3p.id = c3.parent_id 
  WHERE c3p.parent_id = :cat_id
)

https://www.db-fiddle.com/f/tCjGASjdJ4UP16dHugMzWi/1

【讨论】:

  • 感谢您的回答,当请求顶级类别 id 时效果很好(在上面的数据 cat_id = 1 中),所有 3 层类别项目都会显示,但是当我尝试获取 child/1st sub -category(在上面的数据 cat_id = 2 中),它显示来自它的 childern/2nd 子类别的项目,而不是来自它本身的项目。这个1 2 Seagate SSHD 不见了。
  • @EsaO 我在查询中发现并修复了错误。请测试更新版本。例如 cat_id=2: db-fiddle.com/f/tCjGASjdJ4UP16dHugMzWi/3 它显示所有 4 个 HDD,并且只显示它们。至于 cat_id=5:db-fiddle.com/f/tCjGASjdJ4UP16dHugMzWi/4 它仅显示来自 cat 5 和 6 的监视器
  • 完美!完美无瑕。非常感谢。
猜你喜欢
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 2023-03-13
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
相关资源
最近更新 更多