REGEXP_LIKE help
Hello,
Been scouring the web looking for some help using the REGEXP_LIKE syntax. Haven't found a precise answer, but I think I wrote my own correctly and just wanted to get some validation from other users.
Running Oracle 10.2
Sample Data:
create table test(data varchar2(10));
insert into test values('01W00012');
insert into test values('50321070');
insert into test values('A1391010');
insert into test values('ZZ260010');
insert into test values('29374C01');
insert into test values('A938523A');
insert into test values('23W48AC3');
insert into test values('DKFUGHCK');
insert into test values('09W00032');
insert into test values('94857283');
insert into test values('AB-29348');
insert into test values('98W-8923');
insert into test values('0AW00005');
insert into test values('04300W05');
commit;What I'm trying to do:
I have a table containing millions of work orders. They are all of length 8. I want to find all work orders where the first 2 characters are a digit only, the third character is a 'W', and the last 5 characters are digits only. Anything else I want to throw away. I think I came up with a working expression... but I'm always hesitant when running it against millions of rows. Here was what I did:
select * from test
where regexp_like(data, '(^[0-9]{2}W{1}[[:digit:]]{5})');There are exactly 2 occurrences from up above that match the criteria I'm trying to meet.
Is this expression properly written?
Any help would be greatly appreciated.... reg expressions always make my head spin :(
Hi,
dvsoukup wrote:
Running Oracle 10.2
Sample Data: ...Thanks for posting that; it's really helpful!
What I'm trying to do:
I have a table containing millions of work orders. They are all of length 8. I want to find all work orders where the first 2 characters are a digit only, the third character is a 'W', and the last 5 characters are digits only. Anything else I want to throw away. I think I came up with a working expression... but I'm always hesitant when running it against millions of rows. Here was what I did:
select * from test
where regexp_like(data, '(^[0-9]{2}W{1}[[:digit:]]{5})');There are exactly 2 occurrences from up above that match the criteria I'm trying to meet.
Is this expression properly written?Yes, that's a good regular expression. However, a very important thing about regular expressions is that you should only use them when you really need to. In this case, you can get the results you want more efficiently, and at least as easily, without regular expressions. Here's one way:
SELECT *
FROM test
WHERE TRANSLATE ( data
, '012345678'
, '999999999'
) = '99W99999'
;This will be more efficient than using REGEXP_LIKE, and it sounds like efficiency is important in this case.
If you really want to use a regular expression, there are a couple of small things you can do to make it clearer. (With regular expressions, every little bit helps.)
(a) If you're certain that data is always exactly 8 characters, then you don't need the ^ anchor at the beginning. If you want the regular expression to check that the length is 8 characters, then keep the ^ anchor at the beginning, but use a $ anchor at the end, too, as in the example below. As you posted it, the expression will be TRUE when data is longer than 8 characters, as long as the first 8 characters fit the pattern.
(b) [0-9] is equivalent to [[:digit:]]. Either one is fine, but I find it confusing to use both in the same expression. Use one or the other in both places.
(c) {1} is the default. I would just say 'W' instead of 'W{1}'
(d) You don't need the parentheses in this expression. If parentheses are not needed, but they improve clarity, then it's okay to include them. In this case, I don't think they add anything.
There are exactly 2 occurrences from up above that match the criteria I'm trying to meet.It helps if you post exactly what results you want. For example:
DATA
01W00012
09W00032In this case, I found your description very clear, but it doesn't hurt to post the actual results anyway.
Is this expression properly written?You might consider writing it this way, particularly if you think you'll need to debug it:
SELECT *
FROM test
WHERE REGEXP_LIKE ( data
, '^' || -- beginning of string
'[0-9]{2}' || -- 2 digits
'W' || -- a capital W
'[0-9]{5}' || -- 5 more digits
'$' -- end of string
;As mentioned before, you only need the ^ and $ if you're not sure all the strings are exactly 8 characters.
... reg expressions always make my head spin All the more reason to use TRANSLATE.
Edited by: Frank Kulash on Jul 26, 2012 2:42 PM
Similar Messages
-
REGEXP_LIKE help with literal single-quote
I'm trying to write a check constraint to validate email addresses that may include an apostrophe in the email address. Such as joe.o'[email protected] Here is my sample setup:
create table emails
( email_address varchar2(150)
insert into emails values('[email protected]') ;
insert into emails values('[email protected]') ;
insert into emails values('joey.o''[email protected]') ;
commit;
sql> select * from emails;
EMAIL_ADDRESS
[email protected]
[email protected]
joey.o'[email protected]
alter table emails add constraint email_address_format_ck
CHECK ( REGEXP_LIKE ( email_address, '^[a-z0-9._%-]\'?+@[a-z0-9._%-]+\.mil$','c'));
ERROR at line 2:
ORA-00911: invalid characterIt doesn't like *\'?*
My understanding is this means one or more single-quotes. Anyone know the correct syntax to accept apostrophes?Hi,
jimmyb wrote:
... insert into emails values('joey.o''[email protected]') ;
That's the correct way (actually, that's one correct way) to include a single-quote in a string literal: use 2 single-quotes in a row.
... alter table emails add constraint email_address_format_ck
CHECK ( REGEXP_LIKE ( email_address, '^[a-z0-9._%-]\'?+@[a-z0-9._%-]+\.mil$','c'));Here, the 2nd argument to REGEXP_LIKE is a string literal, just like 'joey.o''[email protected]' was a string literal.
To include a single-quote in the middle of this string literal, do the same thing you did before: use 2 of them in a row:
CHECK ( REGEXP_LIKE ( email_address, '^[a-z0-9._%''-]+@[a-z0-9._%-]+\.mil$','c'));There were a couple of other problems, too.
I'm sure you meant for the apostrophe to be inside the square brackets. Inside square brackets, \ does not function as an escape character. (Actually, single-quote has no special meaning in regular expressions, so there's no need to escape it anyway.)
I'm not sure what the '?' mark was doing; I left it out.
Of course, you'll have trouble adding the CHECK constraint if any existing rows violate it.
Edited by: Frank Kulash on Feb 10, 2012 6:52 PM -
REGEXP_LIKE help - escaping the hyphen
I need to match string that does not contain "dc-ba" - all are literal. It has to return true for all strings that is not "ab-cd".
The hypen is creating the problem. If hypen were not there:
select ('Matched') "Status" from dual where REGEXP_LIKE('def', '[^(^dcba$)]');
Matchedselect ('Matched') "Status" from dual where REGEXP_LIKE('dcba', '[^(^dcba$)]');
no rows returnedEverything is as required to this point, but when I try to apply the same with hypen:
select ('Matched') "Status" from dual where REGEXP_LIKE('dc-ba', '[^(^dc-ba$)]');
Error: ORA-12728: Invalid range in regular expression
If I try to escape the hyphen:
select ('Matched') "Status" from dual where REGEXP_LIKE('dc-ba', '[^(^dc\-ba$)]');
MatchedWhich sould not be the case. It shoudl match all string other than "dc-ba".
Am I doing something wrong?Tubby,
it is not just a question of replacing all the hyphens with something that's "special" that won't mess with the regular expression. First of all, that "special" can never occur in source data. For example, replacing hyphens with tilda could result in rejecting dc~ba:
SQL> select ('Matched') "Status" from dual where REGEXP_LIKE(REPLACE('dc~ba', '-','~'), REPLACE('[^(
^dc-ba$)]', '-','~'));
no rows selected
SQL> Secondly, there is over a dozen special meaning characters in regular expressions, so each of them must be replaced with a chatacter that can not appear in source data.
SY. -
Hi All,
I need to find out wheather given string is alphanumeric or perfect string.
can REGEXP_LIKE help in this?
IF REGEXP_LIKE(string,'[a-z]') THEN
IF REGEXP_LIKE(string,'[0-9]') THEN
string is alphanumeric
END IF;
END IF;
Can we merge the both conditions in single REGEXP_LIKE call?
We need exact match if both conditions means if strings contains alphbets as well as number then only returns true.
Same if string contains only alphabets then return true.
REGEXP_LIKE(string,'[a-z]')
With above command if string contains string as well as number it returns TRUE, but we need exact match if string contains only alphabets then return TRUE.
Thanks for your help.sandeep1983 wrote:
Hi All,
I need to find out wheather given string is alphanumeric or perfect string.
can REGEXP_LIKE help in this?
IF REGEXP_LIKE(string,'[a-z]') THEN
IF REGEXP_LIKE(string,'[0-9]') THEN
string is alphanumeric
END IF;
END IF;
Can we merge the both conditions in single REGEXP_LIKE call?
We need exact match if both conditions means if strings contains alphbets as well as number then only returns true.
Same if string contains only alphabets then return true.
REGEXP_LIKE(string,'[a-z]')
With above command if string contains string as well as number it returns TRUE, but we need exact match if string contains only alphabets then return TRUE.
Thanks for your help.you can use character sets:
regexp_like(string,'[[:alnum:]]')or
regexp_like(string,'[a-zA-Z0-9]') -
Need help on regexp_like
Hi Folks,
Please help me out on my requirement which is based on regexp_like
Example:
prod_id and prod_desc are having values like
1,'SAMUSUNG,NOKIA'
2,'NOKIA,SAMUSUNG,APPLE'
3,'NOKIA,APPLE,SAMUSUNG,HTC'
4,'SAMUSUNG,NOKIA,APPLE,HTC,CELLKON'
I want to fetch the values of prod_id and prod_desc as
prod_desc should have SAMSUNG AND NOKIA BUT NOT HTC
answer is :
1,'SAMUSUNG,NOKIA'
2,'NOKIA,SAMUSUNG,APPLE'Greg.Spall wrote:
Easy enough using the documentation as reference:
http://docs.oracle.com/cd/B12037_01/server.101/b10759/conditions018.htm
WITH D AS(SELECT 1 prod_id, 'SAMUSUNG,NOKIA' prod_desc FROM DUAL UNION ALL
SELECT 2,'NOKIA,SAMUSUNG,APPLE' FROM DUAL UNION ALL
SELECT 3,'NOKIA,APPLE,SAMUSUNG,HTC' FROM DUAL UNION ALL
SELECT 4,'SAMUSUNG,NOKIA,APPLE,HTC,CELLKON' FROM DUAL )
SELECT PROD_ID,PROD_DESC FROM D
WHERE NOT REGEXP_LIKE ( prod_desc, '*HTC*', 'i')
PROD_ID PROD_DESC
1 SAMUSUNG,NOKIA
2 NOKIA,SAMUSUNG,APPLE
2 rows selected.
What if the string contains 'AHTCK'? Would that still be excluded? or only where 'HTC' exists between the commas?
SQL> WITH D AS(SELECT 1 prod_id, 'SAMUSUNG,NOKIA' prod_desc FROM DUAL UNION ALL
2 SELECT 2,'NOKIA,SAMUSUNG,APPLE' FROM DUAL UNION ALL
3 SELECT 3,'NOKIA,APPLE,SAMUSUNG,HTC' FROM DUAL UNION ALL
4 SELECT 4,'NOKIA,SAMUSUNG,AHTCK,APPLE' FROM DUAL UNION ALL
5 SELECT 5,'HTC,NOKIA,SAMUSUNG,APPLE' FROM DUAL UNION ALL
6 SELECT 6,'NOKIA,SAMUSUNG,APPLE,HTC' FROM DUAL UNION ALL
7 SELECT 7,'SAMUSUNG,NOKIA,APPLE,HTC,CELLKON' FROM DUAL UNION ALL
8 SELECT 8,'HTC' FROM DUAL )
9 SELECT PROD_ID,PROD_DESC FROM D
10 WHERE NOT regexp_like(PROD_DESC,',HTC,')
11 AND NOT regexp_like(PROD_DESC,'^HTC,')
12 AND NOT regexp_like(PROD_DESC,',HTC$')
13 AND NOT regexp_like(PROD_DESC,'^HTC$')
14 ;
PROD_ID PROD_DESC
1 SAMUSUNG,NOKIA
2 NOKIA,SAMUSUNG,APPLE
4 NOKIA,SAMUSUNG,AHTCK,APPLE -
Need help in REGEXP_LIKE
Hi All,
i need a help in REGEXP_LIKE for following condition as follows.
a column has value as
ALLOW
TO ALL PERSON
ALLOW ME
in this i have check the following condition.
excepted result:
if i give
REGEXP_LIKE(column_name,'ALL')
Result:
1 row selected
if i give
REGEXP_LIKE(column_name,'ALLOW THIS PERSON')
Result:
0 rows selected.
Thanks & Regards
Sami
Edited by: Sami on Nov 2, 2010 6:08 PM
Edited by: Sami on Nov 2, 2010 6:09 PMPlease use the {noformat}{noformat}tag and post formatted data.
For example, when you type (or copy/paste):
{noformat}select *
from dual;
{noformat}
it will appear as:select *
from dual;
on this forum.
See for FAQ for more tags: http://forums.oracle.com/forums/help.jspa
Regarding your question: what is your exect desired output? It's not 100% clear to me what you want.
If I use your first 'example' I get three rows:SQL> -- generating sample data:
SQL> with t as (
2 select 'ALLOW' col from dual union
3 select 'TO ALL PERSON' from dual union
4 select 'ALLOW ME' from dual
5 )
6 --
7 -- actueal query:
8 --
9 select col
10 from t
11 where regexp_like(col, 'ALL');
COL
ALLOW
ALLOW ME
TO ALL PERSON
3 rows selected. -
Query help using regexp_like
kindly help me on this
DECLARE
STRING1 VARCHAR2(1000) :='NOT ( VIP5';
BEGIN
if regexp_like(string1 ,'NOT \(* VIP5') then
dbms_output.put_line('string1 is correct');
dbms_output.PUT_LINE(STRING1);
end if;
END;problem is STRING1 can be
'NOT ( VIP5 '
OR can be NOT ( VIP5'ie between NOT AND VIP5 brackets will be there with spaces or without spaces
so help me for the output
S
Edited by: oraclehema on Mar 1, 2011 3:38 AMHAI
it is working
using
declare
STRING1 VARCHAR2(1000) :='NOT ( VIP5';
STRING2 VARCHAR2(1000) :='NOT ( ( ( VIP5';
begin
if REGEXP_LIKE( string2, 'NOT[[:space:]]*\([[:space:]]*\([[:space:]]*\([[:space:]]*VIP5') then
dbms_output.put_line('string2 is correct');
dbms_output.PUT_LINE(STRING2);
end if;
end;Edited by: oraclehema on Mar 1, 2011 3:52 AM -
Hi, I am on oracle 11g release 1.
I have the following requirement.
I need to display data the following way from the column,
One alphabet followed by 2 digits (like A00, B20, C12), I know I have to use REGEXP_LIKE, but i am not able to get the correct result.
my first attempt at this is
WITH t1
as
(select '01G50' investor_number from dual
union all
select 'A00' from dual
union all
select 'B20' from dual
union all
select '1234' from dual
select investor_number from t1
where REGEXP_LIKE(investor_number, '[[:alpha:]]');
but this gives
investor_number
01G50
A00
B20
but I want only,
investor_number
A00
B20how do i do that?
Thanks
Billu.Hi, Billu,
If you only want to consider the letters that come at the beginning of the string, then anchor the pattern to the beginning of the string, like this:
SELECT investor_number
FROM t1
WHERE REGEXP_LIKE ( investor_number
, '^[[:alpha:]][[:digit:]]{2}'
;You could also write it this way, for clarity:
SELECT investor_number
FROM t1
WHERE REGEXP_LIKE ( investor_number
, '^' || -- Right at the beginning of the string, there must be
'[[:alpha:]]' || -- one letter, followed by
'[[:digit:]]{2}' -- two numerals
;It doesn't matter what (if anything) comes after the 2 digits: another digit ('B209'), a letter ('B20XYZ'), any other character ('B20-9-XYZ'), or nothing (that is, the end-of-string) are all okay.
If you want to find strings that contain only the pattern, and nothing after that, then anchor the patttern to the end-of-string ('$') also:
SELECT investor_number
FROM t1
WHERE REGEXP_LIKE ( investor_number
, '^' || -- Right at the beginning of the string, there must be
'[[:alpha:]]' || -- one letter, followed by
'[[:digit:]]{2}' || -- two numerals, and then
'$' -- the string must end
;Edited by: Frank Kulash on Sep 7, 2010 12:48 PM -
Help with REGEXP_LIKE statement
Hello Experts
I am having little problem in solving the problem with REGEXP_LIKE as shown below.
All the records are giving me the desired result except the last one where it has alph and numeric and spaces in between.
Can I please have the solution please. I tried with INSTR but it didn't work too.
Thanks in advance
Rajesh
WITH T AS
(SELECT '000 444$888' STUDENT_ID FROM DUAL UNION ALL
SELECT '^^^^^^^^^^ ' STUDENT_ID FROM DUAL UNION ALL
SELECT 'ABCDEFGH&' STUDENT_ID FROM DUAL UNION ALL
SELECT '!@@@@@@@ ' STUDENT_ID FROM DUAL UNION ALL
SELECT '123456*891 ' STUDENT_ID FROM DUAL UNION ALL
SELECT 'AAA 77BBBBB ' STUDENT_ID FROM DUAL
SELECT student_id FROM T
WHERE not REGEXP_LIKE(trim(STUDENT_ID), '^[[:alnum:]]*$')Rb2000rb65 wrote:
Thanks Sven. But as you mentioned it did not solve my problem.My first two variants didn't work? Maybe you should start again and explaining which lines you want to see, which not and why.
So far you only mentioned, that the last line gives you trouble. Whatever that means.
/* this is your output */
WITH T AS
(SELECT '000 444$888' STUDENT_ID FROM DUAL UNION ALL
SELECT '^^^^^^^^^^ ' STUDENT_ID FROM DUAL UNION ALL
SELECT 'ABCDEFGH&' STUDENT_ID FROM DUAL UNION ALL
SELECT '!@@@@@@@ ' STUDENT_ID FROM DUAL UNION ALL
SELECT '123456*891 ' STUDENT_ID FROM DUAL UNION ALL
SELECT 'AAA 77BBBBB ' STUDENT_ID FROM DUAL
SELECT student_id FROM T
WHERE not REGEXP_LIKE(trim(STUDENT_ID), '^[[:alnum:]]*$')
000 444$888
^^^^^^^^^^
ABCDEFGH&
123456*891
AAA 77BBBBB
/* this is my output */
WITH T AS
(SELECT '000 444$888' STUDENT_ID FROM DUAL UNION ALL
SELECT '^^^^^^^^^^ ' STUDENT_ID FROM DUAL UNION ALL
SELECT 'ABCDEFGH&' STUDENT_ID FROM DUAL UNION ALL
SELECT '!@@@@@@@ ' STUDENT_ID FROM DUAL UNION ALL
SELECT '123456*891 ' STUDENT_ID FROM DUAL UNION ALL
SELECT 'AAA 77BBBBB ' STUDENT_ID FROM DUAL
SELECT student_id FROM T
WHERE REGEXP_LIKE(STUDENT_ID, '[^[:alnum:] ]')
000 444$888
^^^^^^^^^^
ABCDEFGH&
123456*891 As you can see the last line is missing now. I thought that is what you wanted?
Edited by: Sven W. on Oct 12, 2012 6:42 PM -
Help in regular expression matching
I have three expressions like
1) [(y2009)(y2011)]
2) [(y2008M5)(y2011M3)] or [(y2009M5)(y2010M12)]
3) [(y2009M1d20)(y2011M12d31)]
i want regular expression pattern for the above three expressions
I am using :
REGEXP_LIKE(timedomainexpression, '???[:digit:]{4}*[:digit:]{1,2}???[:digit:]{4}*[:digit:]{1,2}??', 'i');
but its giving results for all above expressions while i want different expression for each.
i hav used * after [:digit:]{4}, when i am using ? or . then its giving no results. Please help in this situation ASAP.
ThanksI dont get your question Can you post your desired output? and also give some sample data.
Please consider the following when you post a question.
1. New features keep coming in every oracle version so please provide Your Oracle DB Version to get the best possible answer.
You can use the following query and do a copy past of the output.
select * from v$version 2. This forum has a very good Search Feature. Please use that before posting your question. Because for most of the questions
that are asked the answer is already there.
3. We dont know your DB structure or How your Data is. So you need to let us know. The best way would be to give some sample data like this.
I have the following table called sales
with sales
as
select 1 sales_id, 1 prod_id, 1001 inv_num, 120 qty from dual
union all
select 2 sales_id, 1 prod_id, 1002 inv_num, 25 qty from dual
select *
from sales 4. Rather than telling what you want in words its more easier when you give your expected output.
For example in the above sales table, I want to know the total quantity and number of invoice for each product.
The output should look like this
Prod_id sum_qty count_inv
1 145 2 5. When ever you get an error message post the entire error message. With the Error Number, The message and the Line number.
6. Next thing is a very important thing to remember. Please post only well formatted code. Unformatted code is very hard to read.
Your code format gets lost when you post it in the Oracle Forum. So in order to preserve it you need to
use the {noformat}{noformat} tags.
The usage of the tag is like this.
<place your code here>\
7. If you are posting a *Performance Related Question*. Please read
{thread:id=501834} and {thread:id=863295}.
Following those guide will be very helpful.
8. Please keep in mind that this is a public forum. Here No question is URGENT.
So use of words like *URGENT* or *ASAP* (As Soon As Possible) are considered to be rude. -
Query help in regular expression
Hi all,
SELECT * FROM emp11
WHERE INSTR(ENAME,'A',1,2) >0;
Please let me know the equivalent query using regular expressions.
i have tried this after going through oracle regular expressions documentation.
SELECT * FROM emp11
WHERE regexp_LIKE(ename,'A{2}')
Any help in this regard would be highly appreciated .
Thanks,
P Prakashplease go here
Introduction to regular expressions ...
Thanks,
P Prakash -
Help With Regular Expression In Apex Validation
Apex 3.2
There is a validation type of regular expression in apex, but I have never used regular expression before,
so a little help is appreciated.
I need to validate a field. It is only allowed to contain alpha characers, numbers, spaces and the - (dash) character.
I have tried several times to get this working
eg
[[:alpha:]]*[[:digit:]]*[[:space:]]*[-]*
^[[:alpha:][:digit:][:space:]-]+?
and others, but just can't to get the syntax correct.
Can someone help me with this please
GusExample:
SQL> ed
Wrote file afiedt.buf
1 with t as (select 'This is some example text' as txt from dual union all
2 select 'And this is the 2nd one with numbers' from dual union all
3 select 'And this allows double-barrelled words with hyphens' from dual union all
4 select 'But this one shouldn''t be allowed!' from dual
5 )
6 --
7 select *
8 from t
9* where regexp_like(txt, '^[[:alnum:] -]*$')
SQL> /
TXT
This is some example text
And this is the 2nd one with numbers
And this allows double-barrelled words with hyphens -
Here is my situation. I have a table that has a list of codes almost 100K. I have another table that has code listed in term of an in house regular expression.
Example:
40a.[1,2,3]
12b
Where
a is 0 - 9
b is 1 - 9
I have tried using REGEXP_LIKE but I get ORA-04030: out of process memory error.
My question is there a way to do this search such that it will be fast and efficient.
I have through about expanding the Expressed code, but that could lead to a lot of codes, and it specially gets tricky if the code is in the format of "1a2b". In this case I would need to somehow create 90 (10*9) rows. I am not entriely sure how to do this dynamically, because there could be a lot of variations.
The current approcach I am thinking of is to search based on character placement. Such that each character becomes a column and I do the comparisson as
Base_Char_1 = Code_Exp_1
Base_Char_2 = Code_Exp_2
I have not figured out how this would work. Shown below is the REGEXP_LIKE approach. Any help or advice would be great.
WITH t1 AS
(SELECT '40a.[0,1,9]1' AS code_exp
FROM DUAL
), t2 AS
(SELECT code_exp
, '^' || REPLACE (REPLACE (REPLACE (REPLACE (code_exp, 'a', '[0-9]'), '.', '\.'), 'b', '[1-9]'), ',') || '$' AS code_regexp
FROM t1)
SELECT *
FROM t2
WHERE REGEXP_LIKE ('402.11', code_regexp)Thanks.Well, it is probably a design issue - joining 100 000 codes with 10 000 regular expressions based on regexp_like() will effectively mean 1e9 calculated regular expressions, which means a lot of work i suppose.
Besides that, there is indeed something strange on pga/uga memory consumption when regular expressions are stored in the table. I've set up small test case based on your data
SQL> CREATE TABLE codes AS
2 SELECT dbms_random.string('p',10) code
3 FROM dual
4 CONNECT BY LEVEL <=100000
5 UNION ALL
6 SELECT '402.11' FROM dual
7 /
Table created.
SQL> CREATE TABLE code_expressions AS
2 WITH t1 AS
3 (SELECT '40a.[0,1,9]1' AS code_exp
4 FROM DUAL
5 ), t2 AS
6 (SELECT code_exp, '^' ||
7 REPLACE (REPLACE (REPLACE (REPLACE (code_exp, 'a', '[0-9]'), '.', '\.'), 'b', '[1-9]'), ',')
8 || '$' AS code_regexp
9 FROM t1)
10 SELECT * FROM t2
11 /
Table created.
SQL> exec dbms_stats.gather_table_stats(user,'codes')
PL/SQL procedure successfully completed.
SQL> exec dbms_stats.gather_table_stats(user,'code_expressions')
PL/SQL procedure successfully completed.
SQL> set lines 100
SQL> col code for a15
SQL> col code_exp for a15
SQL> col code_regexp for a25
SQL> exec runStats_pkg.rs_start;
PL/SQL procedure successfully completed.
SQL> SELECT * FROM codes,code_expressions WHERE regexp_like(code,'^40[0-9]\.[019]1$');
CODE CODE_EXP CODE_REGEXP
402.11 40a.[0,1,9]1 ^40[0-9]\.[019]1$
SQL> exec runStats_pkg.rs_middle;
PL/SQL procedure successfully completed.
SQL> SELECT * FROM codes,code_expressions WHERE regexp_like(code,code_regexp);
CODE CODE_EXP CODE_REGEXP
402.11 40a.[0,1,9]1 ^40[0-9]\.[019]1$
SQL> exec runStats_pkg.rs_stop;
Run1 ran in 34 hsecs
Run2 ran in 276 hsecs
run 1 ran in 12.32% of the time
Name Run1 Run2 Diff
STAT...session cursor cache co 1 0 -1
.... sniped
STAT...CPU used when call star 37 276 239
STAT...CPU used by this sessio 37 276 239
STAT...DB time 37 277 240
STAT...Elapsed Time 36 283 247
STAT...session pga memory 65,536 0 -65,536
STAT...session uga memory 65,560 0 -65,560
STAT...session pga memory max 262,144 10,551,296 10,289,152
STAT...session uga memory max 261,964 10,592,024 10,330,060
Run1 latches total versus runs -- difference and pct
Run1 Run2 Diff Pct
1,009 1,348 339 74.85%
PL/SQL procedure successfully completed.
SQL>
SQL> conn scott/tiger
Connected.
SQL> set lines 100
SQL> col code for a15
SQL> col code_exp for a15
SQL> col code_regexp for a25
SQL>
SQL> exec runStats_pkg.rs_start;
PL/SQL procedure successfully completed.
SQL> SELECT * FROM codes,code_expressions WHERE regexp_like(code,'^40[0-9]\.[019]1$');
CODE CODE_EXP CODE_REGEXP
402.11 40a.[0,1,9]1 ^40[0-9]\.[019]1$
SQL> exec runStats_pkg.rs_middle;
PL/SQL procedure successfully completed.
SQL> SELECT * FROM codes,code_expressions
2 WHERE regexp_like(code,'^' ||
3 REPLACE (REPLACE (REPLACE (REPLACE (code_exp, 'a', '[0-9]'), '.', '\.'), 'b', '[1-9]'), ',') ||
4 '$');
CODE CODE_EXP CODE_REGEXP
402.11 40a.[0,1,9]1 ^40[0-9]\.[019]1$
SQL> exec runStats_pkg.rs_stop;
Run1 ran in 37 hsecs
Run2 ran in 335 hsecs
run 1 ran in 11.04% of the time
Name Run1 Run2 Diff
STAT...recursive cpu usage 3 2 -1
.... sniped
STAT...CPU used when call star 40 336 296
STAT...CPU used by this sessio 40 336 296
STAT...DB time 40 336 296
STAT...Elapsed Time 39 338 299
STAT...session pga memory 65,536 0 -65,536
STAT...session uga memory 65,560 0 -65,560
STAT...session pga memory max 262,144 10,551,296 10,289,152
STAT...session uga memory max 261,964 10,592,024 10,330,060
Run1 latches total versus runs -- difference and pct
Run1 Run2 Diff Pct
1,022 1,348 326 75.82%
PL/SQL procedure successfully completed.
SQL> explain plan for
2 SELECT * FROM codes,code_expressions WHERE regexp_like(code,'^40[0-9]\.[019]1$');
Explained.
SQL> select * from table(dbms_xplan.display);
PLAN_TABLE_OUTPUT
Plan hash value: 1698472622
| Id | Operation | Name | Rows | Bytes | Cost (%CPU)| Time |
| 0 | SELECT STATEMENT | | 5000 | 205K| 59 (6)| 00:00:01 |
| 1 | MERGE JOIN CARTESIAN| | 5000 | 205K| 59 (6)| 00:00:01 |
| 2 | TABLE ACCESS FULL | CODE_EXPRESSIONS | 1 | 31 | 3 (0)| 00:00:01 |
| 3 | BUFFER SORT | | 5000 | 55000 | 56 (6)| 00:00:01 |
|* 4 | TABLE ACCESS FULL | CODES | 5000 | 55000 | 56 (6)| 00:00:01 |
Predicate Information (identified by operation id):
4 - filter( REGEXP_LIKE ("CODE",'^40[0-9]\.[019]1$'))
16 rows selected.
SQL> explain plan for
2 SELECT * FROM codes,code_expressions WHERE regexp_like(code,code_regexp);
Explained.
SQL> select * from table(dbms_xplan.display);
PLAN_TABLE_OUTPUT
Plan hash value: 3098457583
| Id | Operation | Name | Rows | Bytes | Cost (%CPU)| Time |
| 0 | SELECT STATEMENT | | 5000 | 205K| 57 (2)| 00:00:01 |
| 1 | NESTED LOOPS | | 5000 | 205K| 57 (2)| 00:00:01 |
| 2 | TABLE ACCESS FULL| CODE_EXPRESSIONS | 1 | 31 | 3 (0)| 00:00:01 |
|* 3 | TABLE ACCESS FULL| CODES | 5000 | 55000 | 54 (2)| 00:00:01 |
Predicate Information (identified by operation id):
3 - filter( REGEXP_LIKE ("CODE","CODE_REGEXP"))
15 rows selected.
SQL> explain plan for
2 SELECT * FROM codes,code_expressions WHERE regexp_like(code,'^' ||
3 REPLACE (REPLACE (REPLACE (REPLACE (code_exp, 'a', '[0-9]'), '.', '\.'), 'b', '[1-9]'), ',') ||'$');
Explained.
SQL> select * from table(dbms_xplan.display);
PLAN_TABLE_OUTPUT
Plan hash value: 3098457583
| Id | Operation | Name | Rows | Bytes | Cost (%CPU)| Time |
| 0 | SELECT STATEMENT | | 5000 | 205K| 57 (2)| 00:00:01 |
| 1 | NESTED LOOPS | | 5000 | 205K| 57 (2)| 00:00:01 |
| 2 | TABLE ACCESS FULL| CODE_EXPRESSIONS | 1 | 31 | 3 (0)| 00:00:01 |
|* 3 | TABLE ACCESS FULL| CODES | 5000 | 55000 | 54 (2)| 00:00:01 |
Predicate Information (identified by operation id):
3 - filter( REGEXP_LIKE ("CODE",'^'||REPLACE(REPLACE(REPLACE(REPLACE("CODE_E
XP",'a','[0-9]'),'.','\.'),'b','[1-9]'),',')||'$'))
16 rows selected.Best regards
Maxim -
small query i have data like below ,
Month ProductNo CustomerNo Units
Jan 9001 1001-09 100
jan 9002 1002-09 200
jan 9003 1003-09 300
jan 9001 ABCCustomer 400
Jan 9002 1004-09 500
for any record - if column - customerNo starts with numeric it has to show like CN_****** other wise the same name.
Result should be
Jan 9001 CN_1001-09 100
jan 9002 CN_1002-09 200
jan 9003 CN_1003-09 300
jan 9001 ABCCustomer 400
Jan 9002 CN_1004-09 500
Can some one help to get the queryHi,
try this,
SQL> select *from v$version;
BANNER
Personal Oracle Database 10g Release 10.1.0.2.0 - Production
PL/SQL Release 10.1.0.2.0 - Production
CORE 10.1.0.2.0 Production
TNS for 32-bit Windows: Version 10.1.0.2.0 - Production
NLSRTL Version 10.1.0.2.0 - Production
1 with t as
2 (select 'Jan' Month ,9001 ProductNo, '1001-09' CustomerNo, 100 Units from dual
3 union all
4 select 'jan', 9002 ,'1002-09', 200 from dual
5 union all
6 select 'jan', 9003, '1003-09', 300 from dual
7 union all
8 select 'jan', 9001, 'ABCCustomer', 400 from dual
9 union all
10 select 'Jan', 9002, '1004-09', 500 from dual)
11 select Month,ProductNo,(case when regexp_like(customerno,'^[[:digit:]]') then
12 'CN_'||CustomerNo
13 else
14* CustomerNo end)cudtomer_no, units from t
SQL> /
MON PRODUCTNO CUDTOMER_NO UNITS
Jan 9001 CN_1001-09 100
jan 9002 CN_1002-09 200
jan 9003 CN_1003-09 300
jan 9001 ABCCustomer 400
Jan 9002 CN_1004-09 500or
regexp_like(customerno,'^[0-9]')or
regexp_like(customerno,'^[0123456789]')Edited by: user291283 on Sep 12, 2009 8:22 AM
Edited by: user291283 on Sep 12, 2009 9:24 AM -
Need Help with instr/Regexp for the query
Hi Oracle Folks
I am using Oracle
Oracle Database 11g Enterprise Edition Release 11.1.0.7.0 - 64bit Production
With the Partitioning, OLAP, Data Mining and Real Application Testing options
I have some student responses and the valid values are +/-/O(alphabet)/P and spaces at the end of the sting only not in the middle.
As per my requirement the record number 2 3,4 should be listed from the query but I am getting only one (record 3).
Can we use REG_EXP
Please help.
Thanks in advance.
Rajesh
with x as (
SELECT '+-+-POPPPPPP ' STUDENT_RESPONSE, 1 record_number FROM DUAL union all
SELECT '+--AOPPPPPP++' STUDENT_RESPONSE, 2 record_number FROM DUAL union all
SELECT '+-+- OPPPPPP--' STUDENT_RESPONSE, 3 record_number FROM DUAL union all
SELECT '+-+-9OPPPPPP ' STUDENT_RESPONSE, 4 record_number FROM DUAL )
(SELECT RECORD_NUMBER,
TRIM(STUDENT_RESPONSE) FROM X
WHERE
((INSTR (UPPER(TRIM(STUDENT_RESPONSE)),'-') =0)
OR (INSTR (UPPER(TRIM(STUDENT_RESPONSE)),'+') =0)
OR (INSTR (UPPER(TRIM(STUDENT_RESPONSE)),'O') =0)
OR (INSTR (UPPER(TRIM(STUDENT_RESPONSE)),'P') =0)
OR (INSTR (UPPER(TRIM(STUDENT_RESPONSE)),' ') !=0)
)Hi, Rajesh,
Rb2000rb65 wrote:
Hi Oracle Folks
I am using Oracle
Oracle Database 11g Enterprise Edition Release 11.1.0.7.0 - 64bit Production
With the Partitioning, OLAP, Data Mining and Real Application Testing optionsThanks for posting this (and the WITH clause for the sample data). That's very helpful.
I have some student responses and the valid values are +/-/O(alphabet)/P and spaces at the end of the sting only not in the middle.Are you combining the responses to several qeustions in one VARCHAR2 column? It might be better to have a separate row for each question.
As per my requirement the record number 2 3,4 should be listed from the query but I am getting only one (record 3). What exactly is your requirement? Are you trying to find the rows where student_response contains any of the forbidden characters, or where it contains a space anywhere but at the end of the string?
Can we use REG_EXPYes, but it's easy enough, and probably more efficient, to not use regular expressions in this case:
Here's one way:
SELECT record_number
, student_response
FROM x
WHERE TRANSLATE ( UPPER ( RTRIM (student_response, ' '))
, 'X+-OP'
, 'X'
) IS NOT NULL
;That is, once you remove trailing spaces and all occurrences of '+', '-', 'O' or 'P', then only the forbidden characters are left, and you want to select the row if there are any of those.
If you really, really want to use a regular expression:
SELECT record_number
, student_response
FROM x
WHERE REGEXP_LIKE ( RTRIM (student_response)
, '[^-+OP]' -- or '[^+OP-]', but not '[^+-OP]'. Discuss amongst yourselves
, 'i'
;but, I repeat, this will probably be slower than the first solution, using TRANSLATE.
Edited by: Frank Kulash on Oct 17, 2011 1:05 PM
Edited by: Frank Kulash on Oct 17, 2011 1:41 PM
The following is slightly simpler than TRANSLATE:
SELECT record_number
, student_response
FROM x
WHERE RTRIM ( UPPER ( RTRIM (student_response, ' '))
, '+-OP'
) IS NOT NULL
;
Maybe you are looking for
-
I need some help with my Mac. When I try to add a file in Safari, Google Chrome, Opera or even Skype all the aplications closes appearing an Error. Process: Safari [697] Path: /Applications/Safari.app/Contents/MacOS/Safari Identifi
-
My modem is down and can I get the jump-drive to install OS X Lion?
I was informed by my ISP (Hughes.net) that my modem is not functioning to download large files. They are sending a new modem; in the meantime I paid for the Lion upgrade and cannot install it. Can I get the jump-drive sent to me?
-
Trying to download CS6 on my mac pro. when i click on Download, under my orders, it brings up an error page: JRun Servlet error, 413 Header Length to Large. It's been doing this each time I've tried that last few days. What can I do to download this?
-
when i try to open the camera app or photo library it crashs. i tried restoring and that worked but when i re-synced all my contacts and media the camera app crashed. is there any way to sync up to an earlier date? im thinking one of my pics are corr
-
Is it possible to use HTTPS in HTTP recv adapter using Address type as URL
Hi All, If some one who has tried HTTPS communication using HTTP receiver adapter using URL address as Address type can you please guide me what are the steps need to be done. Address type is a parameter in HTTP adapter setup . Regards, Reddy