2017-12-17 2 views
0

3 개의 테이블이 있습니다. 하나는 사용자와 해당 사용자에게 할당 된 요소입니다. 테이블 DDL은 다음과 같습니다.다중 조건으로 계층 구조 결합

CREATE TABLE FSECURE 
    ( "USERID" VARCHAR2(100 BYTE), 
    "F_ELEMENT" VARCHAR2(6 BYTE), 
    "O_ELEMENT" VARCHAR2(20 BYTE), 
    "TYPE" VARCHAR2(20 BYTE) 
    ); 

테이블에 포함 된 데이터는 다음과 같습니다.

REM INSERTING into FSECURE 
SET DEFINE OFF; 
Insert into FSECURE (USERID,F_ELEMENT,O_ELEMENT,TYPE) values ('FFA','140','2003','APP1'); 
Insert into FSECURE (USERID,F_ELEMENT,O_ELEMENT,TYPE) values ('FFA','280','2003','APP1'); 
Insert into FSECURE (USERID,F_ELEMENT,O_ELEMENT,TYPE) values ('GGA','202118','2003','APP2'); 
Insert into FSECURE (USERID,F_ELEMENT,O_ELEMENT,TYPE) values ('GGA','140','2004','APP2'); 
Insert into FSECURE (USERID,F_ELEMENT,O_ELEMENT,TYPE) values ('RFA','202116','3662','APP3'); 
Insert into FSECURE (USERID,F_ELEMENT,O_ELEMENT,TYPE) values ('FFA','110001','3662','APP3'); 

fvol 표 f_secure 테이블의 o_element 컬럼에 대한 참조를 포함한다.

CREATE TABLE FVOL 
     ( "ORG" VARCHAR2(6 BYTE), 
     "ORG_PRED" VARCHAR2(6 BYTE) 
     ); 

REM INSERTING into FVOL 
SET DEFINE OFF; 
Insert into FVOL (ORG,ORG_PRED) values ('2003',null); 
Insert into FVOL (ORG,ORG_PRED) values ('3661','2003'); 
Insert into FVOL (ORG,ORG_PRED) values ('3662','2003'); 
Insert into FVOL (ORG,ORG_PRED) values ('2009',null); 
Insert into FVOL (ORG,ORG_PRED) values ('366X','2009'); 
Insert into FVOL (ORG,ORG_PRED) values ('366P','2009'); 
Insert into FVOL (ORG,ORG_PRED) values ('2004',null); 
Insert into FVOL (ORG,ORG_PRED) values ('1114','2004'); 
Insert into FVOL (ORG,ORG_PRED) values ('2224','2004'); 

fval 표 F- 시큐어 테이블의 f_element에 대한 참조를 포함한다. f_element - - o_element - 유형

그래서 예를에서 계층 구조 노드를 가지고 USER_ID FFA의 경우 내가 데 문제

CREATE TABLE "FVAL" 
    ( "FUND" VARCHAR2(6 BYTE), 
    "FUND_PRED" VARCHAR2(6 BYTE) 
    ); 



    REM INSERTING into FVAL 
SET DEFINE OFF; 
Insert into FVAL (FUND,FUND_PRED) values ('140',null); 
Insert into FVAL (FUND,FUND_PRED) values ('280',null); 
Insert into FVAL (FUND,FUND_PRED) values ('2000','140'); 
Insert into FVAL (FUND,FUND_PRED) values ('20001','2000'); 
Insert into FVAL (FUND,FUND_PRED) values ('20002','2000'); 
Insert into FVAL (FUND,FUND_PRED) values ('20003','2000'); 
Insert into FVAL (FUND,FUND_PRED) values ('202118','2000'); 
Insert into FVAL (FUND,FUND_PRED) values ('2800','280'); 
Insert into FVAL (FUND,FUND_PRED) values ('280001','2800'); 
Insert into FVAL (FUND,FUND_PRED) values ('280002','2800'); 
Insert into FVAL (FUND,FUND_PRED) values ('280003','2800'); 
Insert into FVAL (FUND,FUND_PRED) values ('280004','2800'); 
Insert into FVAL (FUND,FUND_PRED) values ('110001','11000'); 
Insert into FVAL (FUND,FUND_PRED) values ('110002','11000'); 

내가 사용자가 계층 구조를 탐색 할 필요가 있다는 것입니다

FUND:  ORG:   TYPE: 
20001  3661   APP1 
20002  3661   APP1 
20003  3661   APP1 
202118 3661   AAP1 

20001  3662   AAP1 
20002  3662   AAP1 
20003  3663   APP1 
202118 3663   AAP1 
110001 3662   AAP3 
: APP1 그냥 행에 대해 내가 샘플 출력을 검색해야 F_ELEMENT = '140'O_ELEMENT = '2003' 및 TYPE으로 fsecure 테이블

문제는 계층 구조 유형, userid, f_element 및 o_element를 통과하는 것입니다. 계층 구조를 탐색 할 수 있지만 요소를 결합하지 않으면 어떻게 수행 할 것인지에 대한 정신적 차단이 있습니다. 참고 : FFA USER FOR APP3은 해당 행의 일부로 140 및 2003이 없으므로 하나의 f_element 및 o_element 만 가져옵니다.

답변

1

@Miguel는 여기

WITH v_fval 
AS 
(SELECT fund, r_fund 
    FROM (SELECT fund, 
       connect_by_root fund AS r_fund, 
       connect_by_isleaf AS l_fund 
      FROM fval 
     START WITH fund_pred IS NULL 
     CONNECT BY PRIOR fund = fund_pred) 
    WHERE l_fund = 1) 
, v_fvol 
AS 
(SELECT org, r_org 
    FROM (SELECT org, 
       connect_by_root org AS r_org, 
       connect_by_isleaf AS l_org 
      FROM fvol 
      START WITH org_pred IS NULL 
      CONNECT BY PRIOR org = org_pred) 
    WHERE l_org = 1) 
SELECT fsecure.userid, 
     NVL(v_fvol.org, fsecure.o_element) AS org, 
     NVL(v_fval.fund, fsecure.f_element) AS fund, 
     fsecure.type 
    FROM fsecure LEFT JOIN v_fvol 
       ON (fsecure.o_element = v_fvol.r_org) 
       LEFT JOIN v_fval 
       ON (fsecure.f_element = v_fval.r_fund) 
WHERE fsecure.userid = 'FFA' 
ORDER BY fsecure.userid, v_fvol.org, v_fval.fund ; 

출력이

USERID ORG FUND TYPE 
FFA 3661 20001 APP1 
FFA 3661 20002 APP1 
FFA 3661 20003 APP1 
FFA 3661 202118 APP1 
FFA 3661 280001 APP1 
FFA 3661 280002 APP1 
FFA 3661 280003 APP1 
FFA 3661 280004 APP1 
FFA 3662 20001 APP1 
FFA 3662 20002 APP1 
FFA 3662 20003 APP1 
FFA 3662 202118 APP1 
FFA 3662 280001 APP1 
FFA 3662 280002 APP1 
FFA 3662 280003 APP1 
FFA 3662 280004 APP1 
FFA 3662 110001 APP3 

설명 다음과 같다 쿼리

데이터

CREATE TABLE FSECURE 
    ( "USERID" VARCHAR2(100 BYTE), 
    "F_ELEMENT" VARCHAR2(6 BYTE), 
    "O_ELEMENT" VARCHAR2(20 BYTE), 
    "TYPE" VARCHAR2(20 BYTE) 
    ); 
Insert into FSECURE (USERID,F_ELEMENT,O_ELEMENT,TYPE) values ('FFA','140','2003','APP1'); 
Insert into FSECURE (USERID,F_ELEMENT,O_ELEMENT,TYPE) values ('FFA','280','2003','APP1'); 
Insert into FSECURE (USERID,F_ELEMENT,O_ELEMENT,TYPE) values ('GGA','202118','2003','APP2'); 
Insert into FSECURE (USERID,F_ELEMENT,O_ELEMENT,TYPE) values ('GGA','140','2004','APP2'); 
Insert into FSECURE (USERID,F_ELEMENT,O_ELEMENT,TYPE) values ('RFA','202116','3662','APP3'); 
Insert into FSECURE (USERID,F_ELEMENT,O_ELEMENT,TYPE) values ('FFA','110001','3662','APP3'); 

CREATE TABLE FVOL 
     ( "ORG" VARCHAR2(6 BYTE), 
     "ORG_PRED" VARCHAR2(6 BYTE) 
     ); 
Insert into FVOL (ORG,ORG_PRED) values ('2003',null); 
Insert into FVOL (ORG,ORG_PRED) values ('3661','2003'); 
Insert into FVOL (ORG,ORG_PRED) values ('3662','2003'); 
Insert into FVOL (ORG,ORG_PRED) values ('2009',null); 
Insert into FVOL (ORG,ORG_PRED) values ('366X','2009'); 
Insert into FVOL (ORG,ORG_PRED) values ('366P','2009'); 
Insert into FVOL (ORG,ORG_PRED) values ('2004',null); 
Insert into FVOL (ORG,ORG_PRED) values ('1114','2004'); 
Insert into FVOL (ORG,ORG_PRED) values ('2224','2004'); 



CREATE TABLE "FVAL" 
    ( "FUND" VARCHAR2(6 BYTE), 
    "FUND_PRED" VARCHAR2(6 BYTE) 
    ); 
Insert into FVAL (FUND,FUND_PRED) values ('140',null); 
Insert into FVAL (FUND,FUND_PRED) values ('280',null); 
Insert into FVAL (FUND,FUND_PRED) values ('2000','140'); 
Insert into FVAL (FUND,FUND_PRED) values ('20001','2000'); 
Insert into FVAL (FUND,FUND_PRED) values ('20002','2000'); 
Insert into FVAL (FUND,FUND_PRED) values ('20003','2000'); 
Insert into FVAL (FUND,FUND_PRED) values ('202118','2000'); 
Insert into FVAL (FUND,FUND_PRED) values ('2800','280'); 
Insert into FVAL (FUND,FUND_PRED) values ('280001','2800'); 
Insert into FVAL (FUND,FUND_PRED) values ('280002','2800'); 
Insert into FVAL (FUND,FUND_PRED) values ('280003','2800'); 
Insert into FVAL (FUND,FUND_PRED) values ('280004','2800'); 
Insert into FVAL (FUND,FUND_PRED) values ('110001','11000'); 
Insert into FVAL (FUND,FUND_PRED) values ('110002','11000'); 

솔루션 BY CONNECT를 사용하여 솔루션입니다.

2 개의 뷰는 계층 구조의 리프 노드를 가져오고 기본 쿼리가이를 조인합니다. 나는 더 잘 이해하기 위해 견해를 따로 달리기를 제안합니다. 여기

SQL 바이올린 데모 - http://sqlfiddle.com/#!4/a2a751/23

+0

덕분에 당신의 출력을 라 메쉬는 잘 보이지만 당신이 게시 된 쿼리는 내가 그것을 실행할 때 출력되지 않습니다. 데이터를 변경 했습니까? 아마 나는 미안한 것을 미리 놓치고있어. – Miguel

+0

@Miguel - 내가 한 유일한 변경 사항은 레코드 중 하나에서 NULL 주위의 따옴표를 제거하는 것이 었습니다. 데이터도 게시했습니다. 이게 작동하는지 알려주세요. SQL Fiddle 데모도 포함되어 있습니다 - http://sqlfiddle.com/#!4/a2a751/23 – Ramesh

+0

당신은 남자입니다 !! 이것은 마치 매력처럼 작동합니다! 고맙습니다 ! – Miguel