【问题标题】:How to select rows from a hierarchical query filtering by descendant value in Oracle?如何从 Oracle 中按后代值过滤的分层查询中选择行?
【发布时间】:2018-02-17 17:59:42
【问题描述】:

给定表格

ID PARENT_ID STRVAL SUBTYPE SUBVAL 0 null 芝加哥位置城市 1 0 百思买建立百思买 2 0 沃尔玛大楼沃尔玛 3 0 亚马逊建筑亚马逊 4 1 Macbook 对象 macbook 5 2 Sausages 对象香肠 6 3 Macbook 对象 macbook 7 3 特百惠对象 特百惠

我正在尝试做的是查询该表并从 1 级(建筑物)获取所有项目,但我需要做的是通过返回具有包含特定值的子项的那些来过滤此返回集。以下查询是我目前的查询,它返回 Best Buy、Walmart 和 Amazon

SELECT * FROM (
SELECT strval, parent_id, id
FROM stores
where LEVEL = 1
CONNECT BY PRIOR id = parent_id
START WITH parent_id = 0
) 

我想做的是获得一个返回,其中一个后代具有 objectsubtypesubval >macbook,因此从我的查询中只返回 Best BuyAmazon。我真的不确定从这里去哪里。

SQLFiddle

【问题讨论】:

  • SUBTYPE 是否始终与树结构中的级别保持 1:1 的关系? object 总是在第 2 级吗?
  • 对象在某些情况下可能处于第 3 级。

标签: sql oracle recursion oracle11g hierarchical


【解决方案1】:

尝试颠倒您的CONNECT BY 条件并从(即START WITH)您所知道的开始:

SELECT DISTINCT strval, parent_id, id
FROM stores
where subtype = 'building'
CONNECT BY id = prior parent_id
START WITH subtype = 'object' and subval = 'macbook';

更新更一般的问题

在 cmets 中,您问如果起始值不在同一级别怎么办?

在这种情况下,恐怕您必须查看每个建筑物的整棵树,然后进行过滤。

我将此行添加到您的测试数据中:

insert into stores values (8, 4, 'Year','edition','2015');

那么,这个查询给出了答案:

WITH whole_tree AS
       (SELECT strval,
               parent_id,
               id,
               CONNECT_BY_ROOT(strval) building,
               SYS_CONNECT_BY_PATH (subtype || ':' || subval, ',') PATH
        FROM   stores
        CONNECT BY PRIOR id = parent_id
        START WITH subtype = 'building')
SELECT distinct building
FROM   whole_tree
WHERE  PATH LIKE '%object:macbook%edition:2015%';

【讨论】:

  • 这正是我想要的。正如你提到的,我一直在搞乱 CONNECT BY 条件,但我没有考虑在 START WITH 部分设置我的过滤器要求。非常感谢!
  • 如果我要更深一层,其中 Macbook 的 ID 4 有一个子类型为“edition”和子值“2015”的子项,我怎么能只过滤那些 subtype = 'object ' 和 subval = 'macbook' 但也是 'edition' 和子值 '2015' 的后代子类型?
  • 这是一个不同的问题/问题,需要完全不同的方法。你需要一种不同的方法。您可以更新您的问题或提出新问题吗?还有,桌子有多大?
【解决方案2】:

这个连接应该给你父母是建筑物的 macbook 对象。随意选择您只需要的列:

select *
from
(
select *
from stores
where subtype = 'object' 
and strval = 'Macbook'
) macs
join
(
select *
from stores 
where subtype = 'building'
) bld
on bld.id = macs.parent_id

【讨论】:

    猜你喜欢
    • 2015-11-14
    • 1970-01-01
    • 1970-01-01
    • 2019-12-05
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多