Oracle SQL标头和详细信息

时间:2018-06-27 13:34:19

标签: sql oracle

我正在尝试创建标题和明细样式输出,该输出可以输出标题行,然后是明细行,然后是标题行,然后是明细行等。

它将使用两个表:

HeaderTable:

MAIN_NO MAIN_DESCRIPTION MAIN_CUST MAIN_NAME
1       Apple            Student   John
2       Pear             Child     Peter
3       Orange           Alien     Matt

DetailTable:

MAIN_NO PERF EVENT INFO   PREV_VALUE NEW_VALUE REV STATE MODIFIED   NOTE
1       ABC  YES   RED    12         30        0   Con   01/02/2018 FALSE
1       DEF  YES   BLUE   18         34        0   Con   01/04/2018 FALSE
2       GHI  NO    BLUE   14         38        0   UUU   01/07/2018 TRUE
2       JKL  NO    RED    11         39        0   Con   01/03/2018 FALSE
3       MNO  NO    GREEN  19         32        0   UUU   01/01/2018 TRUE
3       PQR  YES   WHITE  10         33        0   UUU   01/08/2018 TRUE

所需的输出:

MAIN_NO MAIN_DESCRIPTION MAIN_CUST MAIN_NAME
1       Apple            Student   John
1       ABC  YES   RED    12         30        0   Con   01/02/2018 FALSE
1       DEF  YES   BLUE   18         34        0   Con   01/04/2018 FALSE
2       Pear             Child     Peter
2       GHI  NO    BLUE   14         38        0   UUU   01/07/2018 TRUE
2       JKL  NO    RED    11         39        0   Con   01/03/2018 FALSE
3       Orange           Alien     Matt
3       MNO  NO    GREEN  19         32        0   UUU   01/01/2018 TRUE
3       PQR  YES   WHITE  10         33        0   UUU   01/08/2018 TRUE

SQL小提琴:http://sqlfiddle.com/#!4/bacd0c

当前代码:

SELECT MAIN_NO, MAIN_DESCRIPTION, MAIN_CUST, MAIN_NAME
FROM 
(
    SELECT MAIN_NO, MAIN_DESCRIPTION, MAIN_CUST, MAIN_NAME, null, null, null, null, null, MAIN_NO rnk 
    FROM HeaderTable

    UNION ALL

    SELECT MAIN_NO, PERF, EVENT, INFO, PREV_VALUE, NEW_VALUE, REV, STATE, MODIFIED,   NOTE, rnk 
    FROM 
    (
        SELECT hd.*, hd.MAIN_NO || '.' || ROW_NUMBER() over (PARTITION BY hd.MAIN_NO ORDER BY hd.MAIN_NO) rnk
        FROM IFSAPP.HeaderTable h 
        INNER JOIN DetailTable hd on h.MAIN_NO= hd.MAIN_NO
    ) K     
)p 
ORDER BY rnk

但是我遇到了错误:

  

ORA-00909:参数数量无效

尽管我什至不确定这是否能给我想要的输出。

2 个答案:

答案 0 :(得分:2)

原始的ORA-00909错误来自concat(),该错误仅包含两个参数。您有三个:

concat(hd.MAIN_NO, '.', ROW_NUMBER() over (PARTITION BY hd.MAIN_NO ORDER BY hd.MAIN_NO))

您需要嵌套调用:

concat(concat(hd.MAIN_NO, '.'), ROW_NUMBER() over (PARTITION BY hd.MAIN_NO ORDER BY hd.MAIN_NO)))

或使用||运算符:

hd.MAIN_NO || '.' || ROW_NUMBER() over (PARTITION BY hd.MAIN_NO ORDER BY hd.MAIN_NO)

但是,如评论中所述,您还有其他问题;解决了concat问题后,出现了“ ORA-01789:查询块的结果列数不正确”错误。 (与修改后的问题一样。)您可以使用null来解决此问题,注释中也建议使用null。但是您的rnk列也是不同的类型-第一个分支使用表格中的数字,第二个分支使用字符串-它将得到“ ORA-01790:表达式必须具有与相应表达式相同的数据类型”。

我认为您只想将标头视为main_no中的等级0,就完全避免了串联:

SELECT MAIN_NO, MAIN_DESCRIPTION, MAIN_CUST, MAIN_NAME,
  PREV_VALUE, NEW_VALUE, REV, STATE, MODIFIED, NOTE
FROM (
    SELECT MAIN_NO, MAIN_DESCRIPTION, MAIN_CUST, MAIN_NAME,
        null as prev_value, null as new_value, null as rev, null as state,
        null as modified, null as note, 0 rnk
    FROM HeaderTable
    UNION ALL
    SELECT hd.MAIN_NO, hd.PERF, hd.EVENT, hd.INFO,
        hd.PREV_VALUE, hd.NEW_VALUE, hd.REV, hd.STATE, hd.MODIFIED, hd.NOTE,
        ROW_NUMBER() over (PARTITION BY hd.MAIN_NO ORDER BY hd.MAIN_NO) as rnk
    FROM HeaderTable h 
    INNER JOIN DetailTable hd on h.MAIN_NO= hd.MAIN_NO
)
ORDER BY main_no, rnk
/

   MAIN_NO MAIN_D MAIN_CU MAIN_ PREV_VALUE  NEW_VALUE        REV STA MODIFIED   NOTE
---------- ------ ------- ----- ---------- ---------- ---------- --- ---------- -----
         1 Apple  Student John
         1 ABC    YES     RED           12         30          0 Con 01/02/2018 FALSE
         1 DEF    YES     BLUE          18         34          0 Con 01/04/2018 FALSE
         2 Pear   Child   Peter
         2 GHI    NO      BLUE          14         38          0 UUU 01/07/2018 TRUE
         2 JKL    NO      RED           11         39          0 Con 01/03/2018 FALSE
         3 Orange Alien   Matt
         3 MNO    NO      GREEN         19         32          0 UUU 01/01/2018 TRUE
         3 PQR    YES     WHITE         10         33          0 UUU 01/08/2018 TRUE

我也删除了一些不必要的子查询;您需要一个以阻止rnk包含在最终结果集中。

最近发现您将为数据添加一个SQL Fiddle; here's the result for that

您可以将null显式转换为期望的数据类型,但这不是必须的;我只是为了好玩而in this db<>fiddle demo,将您的示例数据保存在CTE中。

答案 1 :(得分:1)

为什么第二选择有两次 MAIN_NO

看起来像错字。

MAIN_NO,MAIN_DESCRIPTION,MAIN_CUST,MAIN_NAME, MAIN_NO