简体   繁体   中英

How to get either a child or a parent record SQL

If I have a table that has an uniqueidentifier primary key called Id and there is a column called parentId, that points to another record in the same table that it may be linked to (column is null for parent records, child records have the Id of the parent record), how would I search and pull back a child record if one exists, and the parent record if there are no children? I am searching this table with data from another column that's not the primary key.

I believe what you are looking for is Connect By Level.

https://asktom.oracle.com/pls/apex/f?p=100:11:0::::P11_QUESTION_ID:489772591421

I took the code from the above link and put it below. I hate dead links so this will keep the answer alive here on Stackoverflow.

I don't like providing examples that utilize DDL's as not everyone has the database privileges to create tables etc... The example below works with just plain SQL (Only uses DML). I like using With Blocks to form my tables in easy examples like this one (aka Common Table Expression - CTE).

WITH sample_data AS
(
    SELECT 'KING'   AS ENAMe, 7839 AS EMPNO, NULL AS MGR FROM DUAL UNION ALL
    SELECT 'JONES'  AS ENAMe, 7566 AS EMPNO, 7839 AS MGR FROM DUAL UNION ALL
    SELECT 'SCOTT'  AS ENAMe, 7788 AS EMPNO, 7566 AS MGR FROM DUAL UNION ALL
    SELECT 'ADAMS'  AS ENAMe, 7876 AS EMPNO, 7788 AS MGR FROM DUAL UNION ALL
    SELECT 'FORD'   AS ENAMe, 7902 AS EMPNO, 7566 AS MGR FROM DUAL UNION ALL
    SELECT 'SMITH'  AS ENAMe, 7369 AS EMPNO, 7902 AS MGR FROM DUAL UNION ALL
    SELECT 'BLAKE'  AS ENAMe, 7698 AS EMPNO, 7839 AS MGR FROM DUAL UNION ALL
    SELECT 'ALLEN'  AS ENAMe, 7499 AS EMPNO, 7698 AS MGR FROM DUAL UNION ALL
    SELECT 'WARD'   AS ENAMe, 7521 AS EMPNO, 7698 AS MGR FROM DUAL UNION ALL
    SELECT 'MARTIN' AS ENAMe, 7654 AS EMPNO, 7698 AS MGR FROM DUAL UNION ALL
    SELECT 'TURNER' AS ENAMe, 7844 AS EMPNO, 7698 AS MGR FROM DUAL UNION ALL
    SELECT 'JAMES'  AS ENAMe, 7900 AS EMPNO, 7698 AS MGR FROM DUAL UNION ALL
    SELECT 'CLARK'  AS ENAMe, 7782 AS EMPNO, 7839 AS MGR FROM DUAL UNION ALL
    SELECT 'MILLER' AS ENAMe, 7934 AS EMPNO, 7782 AS MGR FROM DUAL
)

SELECT lpad(' ',LEVEL*2,' ')||ename ename, empno, mgr
FROM sample_data
START WITH MGR IS NULL
CONNECT BY PRIOR EMPNO = MGR
;

Screenshot below to show it in action.

在此处输入图片说明

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM