I want to recognize TIMESTAMP in PostgreSQL by using regexp:
SELECT substring('13:14:00', '([0-1][0-9]|2[0-3]):[0-5]\d:[0-5]\d')
This query returns 13, but I need to receive result 13:14:00.
Analogical query SELECT substring('134', '1(2|3)4') returns 3 instead of 134.
So, what is the problem? My psql version is 9.3.1.
Add parenthesis:
SELECT substring('13:14:00', '(([0-1][0-9]|2[0-3]):[0-5]\d:[0-5]\d)');
Related
I am using REGEXP_EXTRACT function in Google BigQuery to extract a specific word from a string. While regexp works good when tested, function REGEXP_EXTRACT returns null in Google BigQuery.
For example, there is string "RR_SM_Brand_A_Additive_Clean_jun2020", and I want to extract a value from the list (Brand_A, Brand_B, Brand_C, etc.)
When I test RegExp, I receive correct value Brand_A: https://regexr.com/5tecm
RegExp Code: Brand_A|Brand_B (thanks to #Barmar)
But when I run it in Google BigQuery:
SELECT distinct utm_campaign, -- REGEXP_EXTRACT(utm_campaign, r"(?:Brand_A|Brand_B)") REGEXP_EXTRACT(utm_campaign, r"Brand_A|Brand_B") FROM project.dataset.table WHERE utm_campaign = "RB_Display_Brand_A_Botanica_2020"
I receive "This query returned no results.", and not expected Brand_A value.
Note: BigQuery does not return "Cannot parse regular expression: invalid perl operator: (?<"." like in question "duplicate"
I'd suggest that your WHERE clause may be at issue. Both forms you use extract the brand string you appear to be asking for. If the REGEXP_EXTRACT was not matching you'd still get rows, but the value would be NULL.
Converting this to just use the literal from your existing where clause:
SELECT
val,
REGEXP_EXTRACT(val, r"(?:Brand_A|Brand_B)"),
REGEXP_EXTRACT(val, r"Brand_A|Brand_B")
FROM
(
SELECT "RB_Display_Brand_A_Botanica_2020" as val
)
Our Django application just migrated from MySQL to PostgreSQL, and we are in the process of updating our user queries to use the correct syntax. These queries are stored/executed via Django-SQL-Explorer.
I have a query that for simplicity's sake looks like this:
SELECT * FROM table t WHERE t.scheduled_start_date BETWEEN $$from_date$$ AND $$to_date$$
The query above works, but I would like to set defaults for today & today+30 respectively.
I've tried the following WHERE clauses to no avail:
Works with user entered date, default throws syntax error
WHERE t.scheduled_start_date BETWEEN date('$$from_date:CURRENT_DATE$$') AND date('$$to_date:CURRENT_DATE + INTERVAL \'30 DAY\'$$')
Error using defaults:
syntax error at or near "30" LINE 28: ...urrent_date') AND date('current_date + interval \'30 day\'') ^
Defaults work correctly, but user entered dates do not:
WHERE t.scheduled_start_date BETWEEN date($$from_date:CURRENT_DATE$$) AND date($$to_date:CURRENT_DATE + INTERVAL '30 DAY'$$)
Error with user dates:
function date(integer) does not exist LINE 28: WHERE t.scheduled_start_date BETWEEN date(2019-09-30) AND da... ^ HINT: No function matches the given name and argument types. You might need to add explicit type casts.
The message about casting makes sense to me since the user enters in string data, however I can't seem to get the syntax right that casts to DATE but only when the default is overridden.
Any suggestions would be helpful. Thanks!
Your input is a string value, current_date is a function call. The former needs quotes whereas the latter does not. Therefore your client side substitution will not work. You can move the default logic into the SQL statement using the COALESCE() function doc.
In case the client sends NULL values for an empty user input this would result in the following where clause:
BETWEEN date(COALESCE('$$from_date$$',current_date))
AND date(COALESCE('$$from_date$$',current_date + interval '30 DAYS'))
You added that your client sends an empty string, not a NULL value. So this should be changed to:
BETWEEN COALESCE(NULLIF('$$from_date$$','')::date, current_date)
AND COALESCE(NULLIF('$$from_date$$','')::date, current_date + interval '30 DAYS')
I have table (Oracle DB) with some products:
product_1 150
product_2 250
product_1 test 150
product_3
... etc
I want take data only for “product_1” but not for “product_1 test” with only one condition. I use REGEXP_LIKE for it:
SELECT *
FROM TABLENAME
WHERE REGEXP_LIKE(LOWER(PRODUCT), '.*product_1.*(?!test).*')
But it does not work and return empty result. Where is mistake in syntax of regexp?
Oracle does not support lookaheads.
With the products as you show, you can use this:
SELECT * FROM TABLENAME WHERE REGEXP_LIKE(PRODUCT, 'product_\d+(\s*\d+)*', 'c');
This is only based on the product names you have shown. If it does not catch everything you want, give us a better idea of what we are trying to match.
Another option: it's a hack, but if you're confident that "product_digits " should never be followed by a "t", you can use this:
SELECT * FROM TABLENAME WHERE REGEXP_LIKE(PRODUCT, 'product_\d+($|\s)($|[^t]).*', 'c');
Only one condition:
SELECT *
FROM TABLENAME
WHERE
REGEXP_INSTR(LOWER(PRODUCT), 'product_1\s')
> REGEXP_INSTR(LOWER(PRODUCT), 'product_1\s+test')
I am trying to make unique slug URL in oracle using with regular expression. How can I get numeric value end of URL like that lorem-ipsum-dolor-2. My purpose that; Before I check inserted title if exist on table, check it numeric value end of URL if exist slug URL, if has numeric value increase it and save. I have tried the following regular expression that worked properly in C# but it not work in Oracle.
select regexp_like('lorem-ipsum-dolor-2','(\d+)*$') from dual;
What you are doing is almost correct.
But instead of regexp_like' you need to useregexp_substr`:sp
select regexp_substr('lorem-ipsum-dolor-2','\d+$') from dual;
If you are using oracle APEX, and I can assume that's the case if you are working with URLs, than you can use
select apex_string_util.to_slug('Any, Text!;') from dual;
>> any-text
I have a table with one column having a large json object in the format below. The column datatype is VARCHAR
column1
--------
{"key":"value",....}
I'm interested in the first value of the column data
in regex I can do it by .*?:(.*),.* with group(1) giving me the value
How can i use it in the select query
Don't do that, it's bad database design. Shred the keys and values to their own table as columns, or use the XML data type. XML would work fine because you can index the structure well, and you can use XPATH queries on the data. XPATH supports regexp natively.
You can use regular expression with xQuery, you just need to call the function matches from a SQL query or a FLORW query.
This is an example of how to use regular expressions from SQL:
db2 "with val as (
select t.text
from texts t
where xmlcast(xmlquery('fn:matches(\$TEXT,''^[A-Za-z 0-9]*$'')') as integer) = 0
)
select * from val"
For more information:
http://pic.dhe.ibm.com/infocenter/db2luw/v10r5/topic/com.ibm.db2.luw.xml.doc/doc/xqrfnmat.html
http://angocadb2.blogspot.fr/2014/04/regular-expressions-in-db2.html
DB2 doesn't have any built in regex functionality, unfortunately. I did find an article about how to add this with libraries:
http://www.ibm.com/developerworks/data/library/techarticle/0301stolze/0301stolze.html
Without regexes, this operation would be a mess. You could make a function that goes through the string character by character to find the first value. Or, if you will need to do more than this one operation, you could make a procedure that parses the json and throws it into a table of keys/values. Neither one sounds fun, though.
In DB2 for z/OS you will have to pass the variable to XMLQUERY with the PASSING option
db2 "with val as (
select t.text
from texts t
where xmlcast(xmlquery('fn:matches($TEXT,''^[A-Za-z 0-9]*$'')'
PASSING t.text as "TEXT") as integer) = 0
)
select * from val"