2011-09-09 76 views
6

我想在Oracle中使用SQL獲取逗號分隔字符串中的第n個元素。Oracle SQL獲取第n個元素正則表達式

我見到目前爲止以下..

SELECT regexp_substr(
    '100016154,5101884LT00001,,,,,100000010892100000012655,L,SEI,5101884LT00001,1,SL,3595.03,00,2,N,N,G,N', 
    '[^,]+', 
    1, 
    7) 
FROM dual; 

但是當元素爲空,即它不工作,,誰能幫助?

+4

當您在RDBMS中看到CSV或其他序列化值時,您知道某事不對。 – NullUserException

+2

@NullUserException,好點。不幸的是,我碰到過很多次:-( – Ollie

回答

4

如果分隔值始終逗號個字母數字,然後你可以嘗試:

SELECT REGEXP_SUBSTR(<delimied_string>, '[[:alnum:]]{0,},', 1, 7) 
    FROM dual; 

爲了得到第七值(包括後面的逗號)。如果它是空的,你只需得到尾隨的逗號(你可以很容易地刪除)。顯然,如果你想要一個除第七個以外的值,那麼把第四個參數值改變成你想要的第n個出現,例如,

SELECT REGEXP_SUBSTR(<delimied_string>, '[[:alnum:]]{0,},', 1, <nth occurance>) 
    FROM dual; 

編輯:由於我愛正則表達式這裏是一個解決方案,也可以去掉尾隨逗號

SELECT REPLACE(
      REGEXP_SUBSTR(<delimied_string>, '[[:alnum:]]{0,},', 1, <nth>), 
      ',' 
     ) 
    FROM dual; 

希望它有助於

+0

+1,這是可行的。 – DCookie

+0

你好,我有同樣的問題,但你的建議不適用於我的情況 我需要從字符串中獲取第三個值 '從雙重選擇'regexp_substr('SENDER,3B13,3,300,,,,','[[:alnum:]] {0,},',1,2);'但我只得到* *,**字符串 您能否告訴我我做錯了什麼? –

1

你可以用一個小竅門做到這一點:首先更換所有逗號用逗號加一個空格,然後跳過該空格:

SQL> with data as 
    2 (select '100016154,5101884LT00001,,,,,100000010892100000012655,L,SEI,5101884LT00001,1,SL,3595.03,00,2,N,N,G,N' txt 
    3  from dual 
    4 ) 
    5 select regexp_substr(txt,'[^,]+',1,7)        seventh_element_wrong 
    6  , replace(txt,',',', ')          with_extra_space_after_comma 
    7  , regexp_substr(replace(txt,',',', '),'[^,]+',1,7)   seventh_element_leading_space 
    8  , substr(regexp_substr(replace(txt,',',', '),'[^,]+',1,7),2) the_seventh_element 
    9 from data 
10/

S WITH_EXTRA_SPACE_AFTER_COMMA 
- ---------------------------------------------------------------------------------------------------------------------- 
SEVENTH_ELEMENT_LEADING_S THE_SEVENTH_ELEMENT 
------------------------- ------------------------ 
1 100016154, 5101884LT00001, , , , , 100000010892100000012655, L, SEI, 5101884LT00001, 1, SL, 3595.03, 00, 2, N, N, G, N 
100000010892100000012655 100000010892100000012655 

Regar ds,
Rob。

1

除非你被困在正則表達式,這個作品,以及:

WITH q AS (
SELECT '100016154,5101884LT00001,,,,,100000010892100000012655,L,SEI,5101884LT00001,1,SL,3595.03,00,2,N,N,G,N' thestring FROM dual 
) 
SELECT SUBSTR(thestring, INSTR(thestring,',',1,6)+1, 
         INSTR(thestring,',',1,7)-INSTR(thestring,',',1,6)-1) "The Element" 
    FROM q; 

The Element 
------------------------ 
100000010892100000012655 

另一種可能性。您尚未指定數據的來源。你可能使用外部表來讀取你的輸入源並通過SQL來處理它嗎?

+0

在聲明中會有三次調用INSTR的開銷,而不是隻調用一次REGEXP_SUBSTR?(我意識到分隔字符串hasn的長度沒有被指定,並且是一個因素) – Ollie

+0

@Ollie,它可能只有通過測量結果才能確定知道。REGEXP_ *函數不是沒有它們自己的開銷問題。 – DCookie

0
SELECT rtrim(regexp_substr('100016154,5101884LT00001,,,,,100000010892100000012655,L,SEI,5101884LT00001,1,SL,3595.03,00,2,N,N,G,N','[^,]{0,}[,]?',1,7),',') 
FROM dual;