regexp_replace / Substr extract string before and after dashes Oracle - sql

I have a string and I am not able to extract the single characters which is bounded by dashes. I wrote Replace(REGEXP_SUBSTR(string,.*-[[:alnum:]]-'),'-') but it is not giving the expected output.
I need,
XTT-D-X-K-345ROCKVIEW-CA Output = > D X K
RT-5-345REDE Output = > 5
FT-5-3-345HOTELWI Output = > 5 3
But I am getting
XTT-D-X-K-
RT-5-
FT-5-3-
I need to add something which I am not able to figure out.Maybe it can be done with just using regexp instead of using replace on regexp.

try use this:
SELECT Replace(REGEXP_SUBSTR(str, '\-([[:alnum:]]\-)+'), '-', ' ') as outstr
FROM (SELECT 'XTT-D-X-K-345ROCKVIEW-CA' AS str FROM dual
UNION ALL SELECT 'RT-5-345REDE' AS str FROM dual
UNION ALL SELECT 'FT-5-3-345HOTELWI' AS str FROM dual

Related

What is the optimum SQL for producing the below output?

The input column has comma separated integer values like
Sample input 1)
1,2,200000,2345323,1200000
Sample Output 1)
1,2,2345323
Sample input 2)
546^515,400000,657180,3
Sample Output 2)
546^515, 657180,3
The output string should filter out all integers which have "5" trailing zeros.
Excising the five-zero numbers is straightforward with regexp_replace(). But it seems we also need to tidy up the commas left behind. This solution has another regexp_replace() to catch the ,, when the excised number is inside the string, and a simple trim() for when the number is the first or last in the string:
with cte as (
select '1,2,200000,2345323,1200000' as str from dual union all
select '546^515,400000,657180,3' as str from dual union all
select '546^515,400000,1200000,657180,3' as str from dual union all
select '54000000,400000,1200000,657180,300000000' as str from dual
)
select trim(both ',' from regexp_replace(regexp_replace(str, '([0-9]+)00000', null),',(,+)',',')) as new_str
from cte
/

Oracle SQL query to convert a string into a comma separated string with comma after every n characters

How can we convert a string of any length into a comma separated string with comma after every n characters. I am using Oracle 10g and above. I tried with REGEXP_SUBSTR but couldn't get desired result.
e.g.: for below string comma after every 5 characters.
input:
aaaaabbbbbcccccdddddeeeeefffff
output:
aaaaa,bbbbb,ccccc,ddddd,eeeee,fffff,
or
aaaaa,bbbbb,ccccc,ddddd,eeeee,fffff
Thanks in advance.
This can be done with regexp_replace, like so:
WITH sample_data AS (SELECT 'aaaaabbbbbcccccdddddeeeeefffff' str FROM dual UNION ALL
SELECT 'aaaa' str FROM dual UNION ALL
SELECT 'aaaaabb' str FROM dual)
SELECT str,
regexp_replace(str, '(.{5})', '\1,')
FROM sample_data;
STR REGEXP_REPLACE(STR,'(.{5})','\
------------------------------ --------------------------------------------------------------------------------
aaaaabbbbbcccccdddddeeeeefffff aaaaa,bbbbb,ccccc,ddddd,eeeee,fffff,
aaaa aaaa
aaaaabb aaaaa,bb
The regexp_replace simply looks for any 5 characters (.{5}), and then replaces them with the same 5 characters plus a comma. The brackets around the .{5} turn it into a labelled subexpression - \1, since it's the first set of brackets - which we can then use to represent our 5 characters in the replacement section.
You would then need to trim the extra comma off the resultant string, if necessary.
SELECT RTRIM ( REGEXP_REPLACE('aaaaabbbbbcccccdddddeeeeefffff', '(.{5})' ,'\1,') ,',') replaced
FROM DUAL;
This worked for me:
WITH strlen AS
(
SELECT 'aaaaabbbbbcccccdddddeeeeefffffggggg' AS input,
LENGTH('aaaaabbbbbcccccdddddeeeeefffffggggg') AS LEN,
5 AS part
FROM dual
)
,
pattern AS
(
SELECT regexp_substr(strlen.input, '[[:alnum:]]{5}', 1, LEVEL)
||',' AS line
FROM strlen,
dual
CONNECT BY LEVEL <= strlen.len / strlen.part
)
SELECT rtrim(listagg(line, '') WITHIN GROUP (
ORDER BY 1), ',') AS big_bang$
FROM pattern ;

PLSQL Getting values from string

I have this varchar2(2000) string:
id=100\nid2=0\nid3=0\dtext='more Text'
and I want to get only the values e.g. more Text or 0 (id3).
I was trying to use a customized SPLIT function, where separator is \n but this only returns me for example id3=0 (in this case I need '0' as result).
How can I do this more efficient?
and I want to get only the values e.g. more Text.
Simply use SUBSTR and INSTR
SQL> WITH DATA AS
2 ( SELECT q'[id=100\nid2=0\nid3=0\dtext='more Text']' str FROM dual
3 )
4 SELECT SUBSTR(str,instr(str, '''')+1,LENGTH(SUBSTR(str,instr(str, '''')))-2) str
5 FROM DATA
6 /
STR
---------
more Text
SQL>
You could get all the values with something like this:
WITH DATA AS
(SELECT q'[id=100\nid2=0\nid3=0\ndtext='more Text']' str FROM dual)
SELECT replace(substr(regexp_substr(str,'(=.+?\n)|(=.+?$)',1,level),2),'\n') v
FROM DATA
CONNECT BY LEVEL <= LENGTH(regexp_replace(str,'([^=]+=.+?\n)|([^=]=.+?$)'))

Oracle RegExp_Like for Two Repeating Digits

I would like to write a regexp_like function which would identify if a string consists of two repeating characters. It would only identify a string that has alternating numbers and only consisting of two unique numbers, but the unique number cannot repeat, it must alternate.
Requirement :
Regular expression should match the pattern for 787878787, but it should NOT match the pattern 787878788
It should NOT consider the pattern like 000000000
I think you want the following:
WITH t1 AS (
SELECT '787878787' AS str FROM dual
UNION
SELECT '787878788' AS str FROM dual
UNION
SELECT '7878787878' AS str FROM dual
UNION
SELECT '78' AS str FROM dual
)
SELECT * FROM t1
WHERE REGEXP_LIKE(str, '^(.)(.)(\1\2)*\1?$')
AND SUBSTR(str, 1, 1) != SUBSTR(str, 2, 1)
This will cover the case (mentioned in the requirements) where the string ends with the same character with which it begins. If you want only digits, replace the . in the regex with \d.
Update:
Here is how the regex breaks down:
^ = start of string
(.) = first character - can be anything - in parentheses to capture it and use it in a backreference
(.) = second character - can be anything
\1 = backreference to first captured group
\2 = backreference to second captured group
(\1\2)* = These should appear together zero or more times
\1? = The first captured group should appear zero or one times
$ = end of the string
Hope this helps.
You might do something like this -
SQL> WITH DATA AS(
2 SELECT '787878787' str FROM dual UNION ALL
3 SELECT '787878788' FROM dual
4 )
5 SELECT *
6 FROM DATA
7 WHERE REGEXP_LIKE(str, '(\d+?)\1')
8 AND SUBSTR(str, 1,1) = SUBSTR(str, -1, 1)
9 /
STR
---------
787878787
SQL>
Since you are dealing only with digits, I used \d.
\d+? will match the digits, and, \1 are the captured digits. The substr in the AND condition is checking whether the first and last digit of the string are same.
Edit : Additional requirement by OP
To avoid the numbers like 00000000, you need to add a NOT condition to the predicate.
SQL> WITH DATA AS
2 ( SELECT '787878787' str FROM dual
3 UNION ALL
4 SELECT '787878788' FROM dual
5 UNION ALL
6 SELECT '787878788' FROM dual
7 )
8 SELECT *
9 FROM DATA
10 WHERE REGEXP_LIKE(str, '(\d+?)\1')
11 AND SUBSTR(str, 1,1) = SUBSTR(str, -1, 1)
12 AND SUBSTR(str, 2,1) <> SUBSTR(str, -1, 1)
13 /
STR
---------
787878787
SQL>
You could try:
^(..)\1*$
Breakdown:
^ - assert beginning of line
(..) - capture the first 2 characters
\1* - repeat the captured group pattern zero or more times
$ - assert end of line
Untested in oracle...

Extract string within delimiters

I have a string {1:F01BPHKPLPKXXX0000000000} from which I need to extract 1:F01BPHKPLPKXXX0000000000 using regex_substr. Can you please help me with this ?
Why use REGEXP_SUBSTR? Using pistol to kill a mouse?
You just need to TRIM those braces.
SQL> WITH DATA AS(
2 SELECT q'[{1:F01BPHKPLPKXXX0000000000}]' STR FROM DUAL)
3 select rtrim(ltrim(str,'{'),'}') str from data
4 /
STR
--------------------------
1:F01BPHKPLPKXXX0000000000
SQL>
What about this:
select regexp_replace('{1:F01BPHKPLPKXXX0000000000}', '{(.*)}', '\1')
from dual
It takes everything between the brackets and outputs that.
This can be much easier if you ask me, using substr:
select substr(var, 2, length(var)-2)
from (select '{1:F01BPHKPLPKXXX0000000000}' var from dual)
Try the following:
SELECT REGEXP_SUBSTR('{1:F01BPHKPLPKXXX0000000000}', '[^{].*[^}]') FROM DUAL
Share and enjoy.
I would just use regexp_replace. I just use the alternation operator, |, so that I ask to replace { at the beginning (using the anchor ^) and } at the end of the string (using the anchor $).
SCOTT#dev> WITH a_tab AS
2 (SELECT '{1:F01BPHKPLPKXXX0000000000}' a_col FROM dual
3 )
4 SELECT regexp_replace (a_col, '^{|}$') FROM a_tab
5 /
REGEXP_REPLACE(A_COL,'^{|}$')
==========================
1:F01BPHKPLPKXXX0000000000