2017-07-27 79 views
0

我從Oracle DB中獲取一個類型爲BLOB的值和XML格式的值。該XML是巨大的,我想以搜索consits「部門」在裏面,例如如何從Oracle中的文本返回一個子字符串

<ElectronicsDepartment> 
     <term>I year</term> 
     <Capacity>60</Capacity> 
</ElectronicsDepartment> 
    <ComputersDepartment> 
     <term>I year</term> 
     <Capacity>65</Capacity> 
    <ComputersDepartment> 
    <MechanicalDepartment> 
     <term>I year</term> 
     <Capacity>65</Capacity> 
    </MechanicalDepartment> 

XML是很長的覆蓋全部條款從我一年一年IV工程專業的字符串。現在我想獲取從DB這樣的結果的詳細信息應該在下面的格式

 Department  Term  Capactity 
     Electronics I year  60 
     Computers  I year  65 
     Mechanical  I year  65 

我一直在嘗試下面的查詢

SELECT Department/(SELECT Department FROM University where Department like '%Department %'), Term, Capacity From University 

但查詢顯示錯誤

ORA-00932: inconsistent datatypes: expected NUMBER got CLOB 
+0

您正試圖將Department值劃分爲另一個值。你想用'/'符號做什麼? –

+0

「/」是from子句 – Sawyer

+0

中子查詢的語法什麼是「大學」 - 一種已經將XML數據提取爲關係形式的視圖?或者是一個具有'department'作爲包含XML的CLOB的表,以及單獨的術語和容量列?這兩者都沒有道理。請將DDL表添加到問題中,並對其他列的內容進行採樣。 –

回答

1

如果你實際上是從包含XML文檔,其中還有你的一個(無效)片段的CLOB開始,那麼你可以使用built-in XML DB的功能是直接從XML中提取數據。

您似乎想要匹配任何以Department結尾的節點,並將該節點名稱的第一部分作爲部門名稱以及其下的術語和容量值進行提取。

你可以做到這一點與XMLTable和合適的XPath,例如:

-- CTE to represent your raw XML CLOB, with dummy root node 
with university (department) as (
select to_clob('<root> 
    <ElectronicsDepartment> 
     <term>I year</term> 
     <Capacity>60</Capacity> 
    </ElectronicsDepartment> 
    <ComputersDepartment> 
     <term>I year</term> 
     <Capacity>65</Capacity> 
    </ComputersDepartment> 
    <MechanicalDepartment> 
     <term>I year</term> 
     <Capacity>65</Capacity> 
    </MechanicalDepartment> 
</root>') from dual 
) 
-- end of CTE, actual query below 
select x.department, x.term, x.capacity 
from university u 
cross join xmltable (
    '//*[ends-with(name(), "Department")]' 
    passing xmltype(u.department) 
    columns department varchar2(20) path 'substring(name(), 1, string-length(name()) - 10)', 
    term varchar2(10) path 'term', 
    capacity number path 'Capacity' 
) x; 

DEPARTMENT   TERM   CAPACITY 
-------------------- ---------- ---------- 
Electronics   I year    60 
Computers   I year    65 
Mechanical   I year    65 

'//*[ends-with(name(), "Department")]'只匹配以Department端節點。 'substring(name(), 1, string-length(name()) - 10)'從該節點名稱中提取除最後10個字符以外的所有內容,獲得Computers或其他任何內容。其他兩列更直接。

如果您需要過濾包含哪些CLOB,則可以在from和與XMLTable的連接之後正常添加where子句,例如,在university表中的時間戳列上進行篩選:

select x.department, x.term, x.capacity 
from university u 
cross join xmltable (
    '//*[ends-with(name(), "Department")]' 
    passing xmltype(u.department) 
    columns department varchar2(20) path 'substring(name(), 1, string-length(name()) - 10)', 
    term varchar2(10) path 'term', 
    capacity number path 'Capacity' 
) x 
where your_timestamp_col >= timestamp '2017-06-01 00:00:00' 
and your_timestamp_col < timestamp '2017-07-01 00:00:00'; 
+0

我如何給上述選擇條款的where子句 – Sawyer

+0

@Sawyer - 做什麼?正常情況下,您可以在'XMLTable(...)x'之後添加'where'子句,但是在提取後是否要過濾特定的部門或術語或容量值,或者限制您查看某些CLOB值原因? –

+0

有一個時間戳記coloumn,所以我想要獲取兩個時間戳 – Sawyer

1

我認爲你的sql是錯誤的。 這/是爲部門然後它需要與數字一起使用。 這個子查詢 (SELECT部門從大學那裏系'%Department%') 返回一個字符串。

然後它不工作。

你可以閱讀有關XML這裏搜索一些文檔: https://docs.oracle.com/cd/B28359_01/appdev.111/b28369/xdb04cre.htm

+0

本文檔從.xml文件獲取XML。我提取的值是一個CLOB對象,我想要的值是字符串 – Sawyer

+1

,但您可以使用[link](https://docs.oracle.com/html/B14258_02/t_xml.htm)來獲取數據以更舒適的方式使用子查詢。 –

+0

+1給予鏈接。我肯定會給出上述答案,但我已經通過閱讀並找到解決方案來對文檔進行研究。它現在耗時,但似乎沒有其他辦法。 – Sawyer

相關問題