sql - Oracle 11 中的递归 SQL 选择查询

标签 sql oracle hierarchical-data

我有 4 个不同的表,bommodulebomitemmapbomitemmodulemapbomparentsubmodule

bom模块表:

CREATE TABLE "BOMMODULE"
(
  "MODULEID"         NUMBER(10,0) NOT NULL ENABLE,
  "ISROOTMODULE"     NUMBER(1,0) NOT NULL ENABLE,
  "MODULENAME"       VARCHAR2(255 CHAR),
  .....
)

bomitem 表:

CREATE TABLE "BOMITEM"
  (
    "ITEMID"     NUMBER(10,0) NOT NULL ENABLE,
    ....
  )

ma​​pbomitemmodule-table:(此表将项目映射到一个或多个模块)。

CREATE TABLE "SSIS2"."MAPBOMITEMMODULE"
  (
    "ITEMID"   NUMBER(10,0) NOT NULL ENABLE,
    "MODULEID" NUMBER(10,0) NOT NULL ENABLE,
    CONSTRAINT "MAP_ITEM_MODULE_FK" FOREIGN KEY ("ITEMID") REFERENCES "BOMITEM" ("ITEMID") ENABLE,
    CONSTRAINT "MAP_MODULE_ITEM_FK" FOREIGN KEY ("MODULEID") REFERENCES "BOMMODULE" ("MODULEID") ENABLE
  )

ma​​pbomparentsubmodule-table:(此表将模块映射到子模块)

CREATE TABLE "MAPBOMPARENTSUBMODULE"
  (
    "PARENTMODULEID" NUMBER(10,0) NOT NULL ENABLE,
    "SUBMODULEID"    NUMBER(10,0) NOT NULL ENABLE,
    CONSTRAINT "PARENTMODULE_SUBMODULE_FK" FOREIGN KEY ("SUBMODULEID") REFERENCES "BOMMODULE" ("MODULEID") ENABLE,
    CONSTRAINT "SUBMODULE_PARENTMODULE_FK" FOREIGN KEY ("PARENTMODULEID") REFERENCES "BOMMODULE" ("MODULEID") ENABLE
  )

想象一下这样的结构。

root module
  submodule 1
    submodule 2
      submodule 3
        submodule 4
          submodule 5
          item 5
          item 6
          item 7
      item 2
      item 3
      item 4
  item 1

我需要找出属于特定 moduleId 的所有项目。应列出所有子模块级别上的所有项目。

我该怎么做?我使用 Oracle 11 作为数据库。

非常感谢您的帮助,非常感谢!

最佳答案

感谢您提出有趣的问题

1 步。为规范的 Oracle 层次结构准备表。

select PARENTMODULEID, SUBMODULEID, 1 HTYPE
from MAPBOMPARENTSUBMODULE

union all

select null, MODULEID, 1 --link root to null parent
from BOMMODULE B
where ISROOTMODULE = 1

union all 

select MODULEID, ITEMID, 2
from MAPBOMITEMMODULE

2步。使用connect by扩展层次结构

select PARENTMODULEID
      ,SUBMODULEID
      ,HTYPE
      ,level
      ,lpad('|', level*3, '|')
from
(
    select PARENTMODULEID, SUBMODULEID, 1 HTYPE
    from MAPBOMPARENTSUBMODULE

    union all

    select null, MODULEID, 1
    from BOMMODULE B
    where ISROOTMODULE = 1

    union all 

    select MODULEID, ITEMID, 2
    from MAPBOMITEMMODULE
) ALL_HIER
connect by prior SUBMODULEID = PARENTMODULEID
       and prior HTYPE = 1 --parent is always module
start with ALL_HIER.PARENTMODULEID is null
order siblings by HTYPE

3步。最后。与值表连接。

select PARENTMODULEID
      ,SUBMODULEID
      ,HTYPE
      ,ALL_VAL.VAL
      ,level
      ,rpad('|', level * 3, ' ') || ALL_VAL.VAL
from
(
    select PARENTMODULEID, SUBMODULEID, 1 HTYPE
    from MAPBOMPARENTSUBMODULE

    union all

    select null, MODULEID, 1
    from BOMMODULE B
    where ISROOTMODULE = 1

    union all 

    select MODULEID, ITEMID, 2
    from MAPBOMITEMMODULE
) ALL_HIER
,(
    select MODULEID VAL_ID, MODULENAME VAL, 1 VTYPE
    from BOMMODULE

    union all

    select ITEMID, 'item '||ITEMID, 2
    from BOMITEM
) ALL_VAL
where ALL_VAL.VAL_ID = ALL_HIER.SUBMODULEID
  and ALL_VAL.VTYPE = ALL_HIER.HTYPE
connect by prior SUBMODULEID = PARENTMODULEID
       and prior HTYPE = 1
start with ALL_HIER.PARENTMODULEID is null
order siblings by HTYPE

关于sql - Oracle 11 中的递归 SQL 选择查询,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/10329221/

相关文章:

sql - 使用计数我只得到一行

mysql - MYSQL多列总和

database - WHENEVER SQLERROR EXIT FAILURE 在 sqlplus 中抛出错误后的评论部分

mysql - 如何将层次信息存储到数据库中?

mysql - 在 SQL 树结构中查找节点

sql - 检查 varbinary(max) 列是否为 null 真的很慢

oracle - 如何使用 "impdp"命令导入带端口号的 .dmp 数据?

.net - 无法为 .NET 中的 Oracle.DataAccess 加载文件或程序集

sql - 获取分层表sql中每一行的级别

sql - oracle嵌套表中的最大行数是多少