REGEXP_REPLACE 替换列表中除特定域之外的电子邮件
REGEXP_REPLACE to replace emails in a list except a specific domain
我是正则表达式的新手。我正在尝试从不属于特定域的列表中删除电子邮件。
例如我有以下电子邮件列表:
John@yahoo.co.in , Jacob@gmail.com, Bob@rediff.com,
Lisa@abc.com, sam@gmail.com , rita@yahoo.com
我只需要获取 gmail id:
Jacob@gmail.com, sam@gmail.com
请注意,逗号分隔符前可能有空格。
感谢任何帮助!
这对你来说可能是一个开始。
SELECT *
FROM ( SELECT REGEXP_SUBSTR (str,
'[[:alnum:]\.\+]+@gmail.com',
1,
LEVEL)
AS SUBSTR
FROM (SELECT ' John@yahoo.co.in , Jacob.foo@gmail.com, Bob@rediff.com,Lisa@abc.com, sam@gmail.com , sam.bar+Whosebug@gmail.com, rita@yahoo.com, foobar '
AS str
FROM DUAL)
CONNECT BY LEVEL <= LENGTH (REGEXP_REPLACE (str, '[^,]+')) + 1)
WHERE SUBSTR IS NOT NULL ;
再举几个例子,但是电子邮件检查器应该遵守各自的 RFC,查看维基百科以进一步了解它们 https://en.wikipedia.org/wiki/Email_address
灵感来自
这是一种使用 CTE 的方法,只是为了解决问题的不同方式。第一步是创建一个包含已解析列表元素的 CTE "table"。然后 select 从那里。 CTE 正则表达式处理 NULL 列表元素。
with main_tbl(email) as (
select ' John@yahoo.co.in , Jacob.foo@gmail.com, Bob@rediff.com,Lisa@abc.com, sam@gmail.com , sam.bar+Whosebug@gmail.com, rita@yahoo.com, foobar '
from dual
),
email_list(email_addr) as (
select trim(regexp_substr(email, '(.*?)(,|$)', 1, level, NULL, 1))
from main_tbl
connect by level <= regexp_count(email, ',')+1
)
-- select * from email_list;
select LISTAGG(TRIM(email_addr), ', ') WITHIN GROUP ( ORDER BY email_addr )
from email_list
where lower(email_addr) like '%gmail.com';
与其抑制与特定域不匹配的电子邮件(在您的示例中,gmail.com
),不如尝试只获取与域匹配的电子邮件:
WITH a1 AS (
SELECT 'John@yahoo.co.in , Jacob@gmail.com, Bob@rediff.com,Lisa@abc.com, sam@gmail.com , rita@yahoo.com' AS email_list FROM dual
)
SELECT LISTAGG(TRIM(email), ',') WITHIN GROUP ( ORDER BY priority )
FROM (
SELECT REGEXP_SUBSTR(email_list, '[^,]+@gmail.com', 1, LEVEL, 'i') AS email
, LEVEL AS priority
FROM a1
CONNECT BY LEVEL <= REGEXP_COUNT(email_list, '[^,]+@gmail.com', 1, 'i')
);
也就是说,Oracle 可能不是最好的工具(您是否将这些电子邮件地址作为列表存储在某个 table 中?如果是这样,那么@GordonLinoff 的评论是恰当的 - 修复您的数据模型如果可以的话)。
我是正则表达式的新手。我正在尝试从不属于特定域的列表中删除电子邮件。
例如我有以下电子邮件列表:
John@yahoo.co.in , Jacob@gmail.com, Bob@rediff.com,
Lisa@abc.com, sam@gmail.com , rita@yahoo.com
我只需要获取 gmail id:
Jacob@gmail.com, sam@gmail.com
请注意,逗号分隔符前可能有空格。 感谢任何帮助!
这对你来说可能是一个开始。
SELECT *
FROM ( SELECT REGEXP_SUBSTR (str,
'[[:alnum:]\.\+]+@gmail.com',
1,
LEVEL)
AS SUBSTR
FROM (SELECT ' John@yahoo.co.in , Jacob.foo@gmail.com, Bob@rediff.com,Lisa@abc.com, sam@gmail.com , sam.bar+Whosebug@gmail.com, rita@yahoo.com, foobar '
AS str
FROM DUAL)
CONNECT BY LEVEL <= LENGTH (REGEXP_REPLACE (str, '[^,]+')) + 1)
WHERE SUBSTR IS NOT NULL ;
再举几个例子,但是电子邮件检查器应该遵守各自的 RFC,查看维基百科以进一步了解它们 https://en.wikipedia.org/wiki/Email_address
灵感来自
这是一种使用 CTE 的方法,只是为了解决问题的不同方式。第一步是创建一个包含已解析列表元素的 CTE "table"。然后 select 从那里。 CTE 正则表达式处理 NULL 列表元素。
with main_tbl(email) as (
select ' John@yahoo.co.in , Jacob.foo@gmail.com, Bob@rediff.com,Lisa@abc.com, sam@gmail.com , sam.bar+Whosebug@gmail.com, rita@yahoo.com, foobar '
from dual
),
email_list(email_addr) as (
select trim(regexp_substr(email, '(.*?)(,|$)', 1, level, NULL, 1))
from main_tbl
connect by level <= regexp_count(email, ',')+1
)
-- select * from email_list;
select LISTAGG(TRIM(email_addr), ', ') WITHIN GROUP ( ORDER BY email_addr )
from email_list
where lower(email_addr) like '%gmail.com';
与其抑制与特定域不匹配的电子邮件(在您的示例中,gmail.com
),不如尝试只获取与域匹配的电子邮件:
WITH a1 AS (
SELECT 'John@yahoo.co.in , Jacob@gmail.com, Bob@rediff.com,Lisa@abc.com, sam@gmail.com , rita@yahoo.com' AS email_list FROM dual
)
SELECT LISTAGG(TRIM(email), ',') WITHIN GROUP ( ORDER BY priority )
FROM (
SELECT REGEXP_SUBSTR(email_list, '[^,]+@gmail.com', 1, LEVEL, 'i') AS email
, LEVEL AS priority
FROM a1
CONNECT BY LEVEL <= REGEXP_COUNT(email_list, '[^,]+@gmail.com', 1, 'i')
);
也就是说,Oracle 可能不是最好的工具(您是否将这些电子邮件地址作为列表存储在某个 table 中?如果是这样,那么@GordonLinoff 的评论是恰当的 - 修复您的数据模型如果可以的话)。