oracle Regex忽略数据某些部分的分隔符

n7taea2i  于 2023-06-22  发布在  Oracle
关注(0)|答案(3)|浏览(129)

当前使用的数据和正则表达式

考虑以下数据;
FDTYP/TESTTYPE/FDPERIOD/31 Day(s)/MAT_INST/CREDIT_TO_ACC/DEPTACCT/0016/
当前用于分隔数据的方法是使用分隔符'/'来获取此数据列表;
{"FDTYP", "TESTTYPE", "FDPERIOD", "31 Day(s)", "MAT_INST", "CREDIT_TO_ACC", "DEPTACCT", "0016" }
这是使用了正则表达式的代码片段;
REGEXP_SUBSTR( ORGDATA ,'(.*?)/|$', 1, COLUMN_VALUE, NULL, 1 ) AS DATALABEL

问题

现在考虑这些数据
FDTYP/FD2323*/*/*-/FDPERIOD/31 Day(s)/MAT_INST/CREDIT_TO_ACC/DEPTACCT/0016/
第二个数据包含定界符'/',它生成以下数据列表
{"FDTYP", "FD2323*", "*", "*-", "FDPERIOD", "31 Day(s)", "MAT_INST", "CREDIT_TO_ACC", "DEPTACCT", "0016" }
正确的数据应该是
{"FDTYP", "FD2323*/*/*-", "FDPERIOD", "31 Day(s)", "MAT_INST", "CREDIT_TO_ACC", "DEPTACCT", "0016" }
现在我知道解决这个问题的最简单的方法是改变使用的分隔符,但不幸的是,由于遗留数据,这是不可能的。
那么有没有办法创建一个regex来忽略第二个数据的分隔符呢?
我尝试了以下正则表达式
(?<=FDTYP\/)(.*?)(?=\/FDPERIOD)
它确实给了我第二个数据,但它对其余的数据不起作用。

6fe3ivhb

6fe3ivhb1#

我不是100%清楚你使用的是哪个版本的SQL,或者你实际上是如何得到JSON的,但是假设问题点总是发生在FDTYPE//FDPERIOD之间,我认为这样的东西应该可以工作:
1.仅将子字符串中/的示例替换为您知道不会在数据集中出现的某些字符或字符组合。在我的示例中,我使用{!}作为替换。
1.你平时有没有
1.返回提取的数据并将替换的{!}转换回/

SELECT
    'FDTYP/FD2323*/*/*-/FDPERIOD/31 Day(s)/MAT_INST/CREDIT_TO_ACC/DEPTACCT/0016/' AS ORGDATA,
    CONCAT('FDTYP/', REPLACE(REGEXP_SUBSTR((SELECT ORGDATA), '(?<=FDTYP/)(.*)(?=/FDPERIOD)'), '/', '{!}'), REGEXP_SUBSTR((SELECT ORGDATA), '/FDPERIOD.*(?=/$)')) AS transformed,
    CONCAT('{"', REPLACE((SELECT transformed), '/', '", "'), '"}') AS object_str,
    REPLACE((SELECT object_str), '{!}', '/') AS untransformed

这让你:

FDTYP/FD2323*/*/*-/FDPERIOD/31 Day(s)/MAT_INST/CREDIT_TO_ACC/DEPTACCT/0016/
FDTYP/FD2323*{!}*{!}*-/FDPERIOD/31 Day(s)/MAT_INST/CREDIT_TO_ACC/DEPTACCT/0016
{"FDTYP", "FD2323*{!}*{!}*-", "FDPERIOD", "31 Day(s)", "MAT_INST", "CREDIT_TO_ACC", "DEPTACCT", "0016"}
{"FDTYP", "FD2323*/*/*-", "FDPERIOD", "31 Day(s)", "MAT_INST", "CREDIT_TO_ACC", "DEPTACCT", "0016"}

https://www.db-fiddle.com/f/4BRg1FG23qhYYFrwFAqqEY/0

byqmnocz

byqmnocz2#

在Oracle中,您可以使用正则表达式'^([^/]+)/(.*)/([^/]+)/([^/]+)/([^/]+)/([^/]+)/([^/]+)/([^/]+)/$'并提取捕获组:

SELECT REGEXP_SUBSTR(
         value,
         '^([^/]+)/(.*)/([^/]+)/([^/]+)/([^/]+)/([^/]+)/([^/]+)/([^/]+)/$',
         1,
         1,
         NULL,
         1
       ) AS col1,
       REGEXP_SUBSTR(
         value,
         '^([^/]+)/(.*)/([^/]+)/([^/]+)/([^/]+)/([^/]+)/([^/]+)/([^/]+)/$',
         1,
         1,
         NULL,
         2
       ) AS col2,
       REGEXP_SUBSTR(
         value,
         '^([^/]+)/(.*)/([^/]+)/([^/]+)/([^/]+)/([^/]+)/([^/]+)/([^/]+)/$',
         1,
         1,
         NULL,
         3
       ) AS col3,
       REGEXP_SUBSTR(
         value,
         '^([^/]+)/(.*)/([^/]+)/([^/]+)/([^/]+)/([^/]+)/([^/]+)/([^/]+)/$',
         1,
         1,
         NULL,
         4
       ) AS col4,
       REGEXP_SUBSTR(
         value,
         '^([^/]+)/(.*)/([^/]+)/([^/]+)/([^/]+)/([^/]+)/([^/]+)/([^/]+)/$',
         1,
         1,
         NULL,
         5
       ) AS col5,
       REGEXP_SUBSTR(
         value,
         '^([^/]+)/(.*)/([^/]+)/([^/]+)/([^/]+)/([^/]+)/([^/]+)/([^/]+)/$',
         1,
         1,
         NULL,
         6
       ) AS col6,
       REGEXP_SUBSTR(
         value,
         '^([^/]+)/(.*)/([^/]+)/([^/]+)/([^/]+)/([^/]+)/([^/]+)/([^/]+)/$',
         1,
         1,
         NULL,
         7
       ) AS col7,
       REGEXP_SUBSTR(
         value,
         '^([^/]+)/(.*)/([^/]+)/([^/]+)/([^/]+)/([^/]+)/([^/]+)/([^/]+)/$',
         1,
         1,
         NULL,
         8
       ) AS col8
FROM   table_name

其中,对于样本数据:

CREATE TABLE table_name (value) AS
  SELECT 'FDTYP/FD2323*/*/*-/FDPERIOD/31 Day(s)/MAT_INST/CREDIT_TO_ACC/DEPTACCT/0016/' FROM DUAL UNION ALL
  SELECT 'FDTYP/TESTTYPE/FDPERIOD/31 Day(s)/MAT_INST/CREDIT_TO_ACC/DEPTACCT/0016/' FROM DUAL

输出:
| COL1| COL2| COL3| COL4| COL5| COL6| COL7| COL8|
| - -----|- -----|- -----|- -----|- -----|- -----|- -----|- -----|
| FDTYP| FD2323*//-|FDPERIOD| 31天|MAT_INST|贷记至ACC|退出|0016|
| FDTYP|测试类型|FDPERIOD| 31天|MAT_INST|贷记至ACC|退出|0016|
或者,以单个格式化字符串的形式获取输出:

SELECT REGEXP_REPLACE(
         value,
         '^([^/]+)/(.*)/([^/]+)/([^/]+)/([^/]+)/([^/]+)/([^/]+)/([^/]+)/$',
         '{"\1", "\2", "\3", "\4", "\5", "\6", "\7", "\8"}'
       ) AS data
FROM   table_name;

其输出:
| 数据|
| - -----|
| {“FDTYP”,“FD2323*//-",“FDPERIOD”,“31天",“MAT_INST”,“CREDIT_TO_ACC”,“DEPTACCT”,“0016”}|
| {“FDTYP”,“TESTTYPE”,“FDPERIOD”,“31天",“MAT_INST”,“CREDIT_TO_ACC”,“DEPTACCT”,“0016”}|
fiddle

n9vozmp4

n9vozmp43#

您可以使用以下内容。

(?<!\*)/

输出量

FDTYP
TESTTYPE
FDPERIOD
31 Day(s)
MAT_INST
CREDIT_TO_ACC
DEPTACCT
0016

FDTYP
FD2323*/*/*-
FDPERIOD
31 Day(s)
MAT_INST
CREDIT_TO_ACC
DEPTACCT
0016

相关问题