首页
学习
活动
专区
圈层
工具
发布
社区首页 >问答首页 >利用REGEXP_SUBSTR提取数据

利用REGEXP_SUBSTR提取数据
EN

Stack Overflow用户
提问于 2018-01-26 09:50:45
回答 5查看 817关注 0票数 0

嗨,我正在尝试使用REGEXP_SUBSTR函数从oracle数据库中提取包含在单个字段中的部分文本。所讨论的案文以黑体字显示在"BRS14774366“下面。好消息是,我试图提取的数据的模式是相当一致的,因为它总是以"-“开头,以"CSN”结尾,但是我一直试图提取的文本并不总是相同的,可以由alpha字符和数字字符组成,长度在1-12个字符之间。

PSN932-52506252-BRS14774366CSN/SF-1/25JAN0524

下面的示例显示了长度上的细微差异,同样,我试图提取的文本以粗体显示。正如您所看到的,位置总是相同的,但是Alpha数字字符可以介于"-“和"CSN”之间,长度不同。

PSN932-49837056-DELAIR09364CSN/SF-66/25JAN0541

PSN932-51231434-H1001865CSN/SF-5/25JAN0546

PSN932-52648256-2EGA814CSN/SF-10/25JAN0549

以第一个示例数据( (PSN932-52506252-BRS14774366CSN/SF-1/25JAN0524) )为例,我创建了以下查询,该查询正确地输出数据,但是该查询不考虑文本可以由两个字符组成,其长度在1-12个字符之间。

选择REGEXP_SUBSTR('PSN932-52506252-BRS14774366CSN/SF-1/25JAN0524',‘-(\D\d\d)’,1,1,'i',1) "REGEXP_SUBSTR“;

上述查询的输出如下:

BRS14774366

有人能告诉我如何在查询中格式化匹配模式,这样我就可以一致地提取"-“和"CSN”之间的数据了吗?

一如既往地感谢人们所能提供的任何帮助?

Update --似乎存储了包含回车的数据,所以下面的查询无法工作:

SELECT REGEXP_SUBSTR('PSN 932-52506252-BRS14774366 CSN/SF-1/25JAN0524', '-(\w+)CSN', 1, 1, 'i', 1) "REGEXP_SUBSTR" FROM DUAL;

如果数据是这样的,那么工作得很好:

代码语言:javascript
复制
SELECT

REGEXP_SUBSTR('PSN932-52506252-BRS14774366CSN/SF-1/25JAN0524','-(\w+)CSN',1,1,'i',1) "REGEXP_SUBSTR“;

这个函数能处理回车吗?

EN

回答 5

Stack Overflow用户

发布于 2018-01-26 10:00:50

这就是你要找的东西吗?

代码语言:javascript
复制
SQL> with
  2    s as (select 'SN932-52506252-BRS14774366CSN/SF-1/25JAN0524' n from dual union all
  3          select 'PSN932-49837056-DELAIR09364CSN/SF-66/25JAN0541' from dual union all
  4          select 'PSN932-51231434-H1001865CSN/SF-5/25JAN0546' from dual union all
  5          select 'PSN932-52648256-2EGA814CSN/SF-10/25JAN0549' from dual)
  6  select
  7    substr(replace(regexp_substr(s.n, '-([[:alpha:]]|[[:digit:]])+CSN'), 'CSN'), 2)
  8  from s;

SUBSTR(REPLACE(REGEXP_SUBSTR(S
--------------------------------------------------------------------------------
BRS14774366
DELAIR09364
H1001865
2EGA814
票数 1
EN

Stack Overflow用户

发布于 2018-01-26 10:21:27

您可以使用\w来匹配任何字母数字字符

Oracle文档

\w字字符,它被定义为字母、数字或下划线()字符。它相当于POSIX类[:alnum:]。注意,如果不想包含下划线字符,可以使用POSIX类[:alnum:]。

因此,应该将模式更改为-(\w+)CSN

删除换行符很可能是通过替换linefeed/carrige返回字符来完成的。

代码语言:javascript
复制
WITH s AS (select 'SN932-52506252-BRS14774366CSN/SF-1/25JAN0524' n from dual union all
       select 'PSN932-49837056-DELAIR09364' || chr(10) || 'CSN/SF-66/25JAN0541' from dual union all
       select 'PSN932-51231434-H1001865CSN/SF-5/25JAN0546' from dual union all
       select 'PSN932-52648256-2EGA814' || chr(13) || 'CSN/SF-10/25JAN0549' from dual),
remove_newlines as (select replace(replace(s.n, chr(10), ''), chr(13), '') n from s)

SELECT regexp_substr(s.n, '-(\w+)CSN', 1, 1, 'i', 1) "REGEXP_SUBSTR" FROM remove_newlines s;
票数 1
EN

Stack Overflow用户

发布于 2018-01-26 10:09:20

通过将instrsubstr组合起来,您可以避免使用正则表达式。

这可能不是那么容易理解,但通常表现比regexp解决方案更好。

代码语言:javascript
复制
 with test(x) as (
        select 'PSN932-49837056-DELAIR09364CSN/SF-66/25JAN0541' from dual union all
        select 'PSN932-51231434-H1001865CSN/SF-5/25JAN0546' from dual union all
        select 'PSN932-52648256-2EGA814CSN/SF-10/25JAN0549' from dual
    )
    select substr(
                    substr(x, 1, instr(x, 'CSN') -1),
                    instr(
                            substr(x, 1, instr(x, 'CSN') -1),
                            '-',
                            -1
                         )+1
                 )
    from test

这部分将由CSN负责:

substr(substr(x, 1, instr(x, 'CSN') -1)

然后从最后一个'-‘开始获取此部分的子字符串:

代码语言:javascript
复制
instr(substr(x, 1, instr(x, 'CSN') -1), '-',-1)+1
票数 0
EN
页面原文内容由Stack Overflow提供。腾讯云小微IT领域专用引擎提供翻译支持
原文链接:

https://stackoverflow.com/questions/48458966

复制
相关文章

相似问题

领券
问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档