行没有被正则表达式捕获

Posted

技术标签:

【中文标题】行没有被正则表达式捕获【英文标题】:Rows not being caught by regular expression 【发布时间】:2016-05-05 22:21:11 【问题描述】:

我在 TOAD V10.6 中编写我的 PL SQL 代码,然后在 Oracle 服务器上运行,我相信是 11g。

因为我正在处理客户广告信息,我实际上无法发布任何结果。

我的程序的目标是将地址数据解析为正确的字段。谢天谢地,它不是整个地址。它确实包含的信息是建筑物编号、街道名称、街道类型、方向和子单元。信息并不总是在同一个演示文稿中,我已经按照我解析信息的顺序来解决这个问题。

我解析地址字段的方式

    我将地址数据加载到一个新表中 我删除了重复的行 我将关键的 adrs 模式标记为错误(例如没有足够的字段,因为地址需要至少 3 个有效) 我提取了可以出现在广告中任何位置的子单元 我提取了可以出现在广告中任何位置的方向 我提取建筑物编号并确保其唯一编号 我查看公寓楼号上是否有连字符 我检查以确保仍然有足够的信息用于有效地址,因为我仍然需要街道类型和名称 我提取街道类型 剩下的都被认为是街道名称

我有 27,000 个正在正确解析,大约 3000 个包含错误并被排除在外,还有 2200 个未正确处理但未触发任何错误,这是最后一步。

  UPDATE TEMP_PARSE_EXIST
    SET V_STREET_TYPE = REGEXP_SUBSTR(ADRS, '\w+.$')
    WHERE ADT_ACT IS NULL;
    UPDATE TEMP_PARSE_EXIST
    SET ADT_ACT = 'EMPTY STREET TYPE'
    WHERE V_STREET_TYPE IS NULL AND ADT_ACT IS NULL;

我之前在解析子单元时遇到了几乎相同的问题。我从来不知道是什么原因造成的,或者为什么将正则表达式从 where 子句移到不同的部分来纠正它。

UPDATE TEMP_PARSE_EXIST
SET ADT_ACT = 'PARSE ERROR: TOO MANY S_COM_RES_TYPE '
WHERE ADT_ACT IS NULL AND V_SECOND_LINE IS NULL 
AND REGEXP_COUNT(ADRS, '\s' || S_COM_RES_TYPE || '.+\s.+' || S_COM_RES_TYPE , 1, 'i') > 1;
--this looks for a space before and after the sub-unit, then anything between another example
--the space before and after are to prevent STE and FL from being matched with valid street names
--the second one is less strict about that
--if there starts to be an issue then a space before can be added
--however, adding a space after would having it miss cases where there is no space after for the unit number
--the block of code below is suspected of being where the error is happening
--the error in question is where suite is not being noticed and extracted from the adrs line
--however there are many more similar examples being correctly handled

    UPDATE TEMP_PARSE_EXIST
    SET V_SECOND_LINE = REGEXP_SUBSTR(ADRS, S_COM_RES_TYPE || '(\s?\w+|$)', 1, 1, 'i')

    --'(\s\w+|$)' was the original expression, but the ? was added in to account for there not being a space
    --so the pattern grabs the sub-unit, and allows for a possible space between it and the number, or allows the end of string as there are some cases of that
    WHERE ADT_ACT IS NULL AND V_SECOND_LINE IS NULL AND REGEXP_COUNT(ADRS,  S_COM_RES_TYPE, 1, 'i') = 1;

--this removes v_second_line from the adrs
UPDATE TEMP_PARSE_EXIST
SET ADRS = TRIMMER(REPLACE(ADRS, V_SECOND_LINE))
WHERE V_SECOND_LINE IS NOT NULL;

下面的代码没有和上面一样的错误

UPDATE TEMP_PARSE_EXIST
SET ADT_ACT = 'PARSE ERROR: TOO MANY S_COM_RES_TYPE '
WHERE REGEXP_like(adrs,  '\s' || S_COM_RES_TYPE || '\s(|.+)' || S_COM_RES_TYPE , 'i');
--this looks for a space before and after the sub-unit, then anything between another example
--the space before and after are to prevent STE and FL from being matched with valid street names
--which is a common issue if I am not so strict about it

UPDATE TEMP_PARSE_EXIST
SET V_SECOND_LINE = trimmer(REGEXP_substr(adrs,  '\s' || S_COM_RES_TYPE || '\s\w+',1,1 ,'i'))
WHERE ADT_ACT IS NULL AND V_SECOND_LINE IS NULL;

--this removes v_second_line from the adrs, this is done for both parts
UPDATE TEMP_PARSE_EXIST
SET ADRS = TRIMMER(REPLACE(ADRS, V_SECOND_LINE))
WHERE V_SECOND_LINE IS NOT NULL;

我无法弄清楚为什么会发生这种情况。 我在我所在的地区进行一个不规则的项目,与我一起工作的人不需要使用正则表达式并且无法帮助我。

所以问题是,为什么有有效的地址使其超过正则表达式?

更新: 以下是正确处理并成功解析所有部分的 adr 示例

Full example adrs            Dirn    Sub-unit  number  type     name  
100 Street1 Dr E             E                 100     Dr       Street1  
1000 1st Ave Suite 501               Suite 501 1000    Ave      1st  
1000 100th St                                  1000    St       100th  
1000 1st Ave N Unit 7        N       Unit 7    1000    Ave      1st  

以下是超出表达式的示例

Full example adrs            Dirn    Sub-unit  number  type     name  
1000 1st Avenue E            E                 1000             1st Avenue  
1000 Street1 Road                              1000             Street1 Road  
1000 Street2 Street                            1000             Street2 Street  
1000 Street3 Drive                             1000             Street3 Drive  
100 1st Avenue S Unit 100    S       Unit 100  100              1st Avenue  

上面列出的所有示例地址都是真实的(我更改了建筑物编号和名称)并且来自同一个数据集。没有多余的字符丢失,例如空格或特殊字符。

【问题讨论】:

您能否添加模拟数据作为示例数据,以便我们实际看到它发生了什么?不需要是真实数据,只需使用模仿真实数据的假数据即可。帮助你会更容易。 请发布您的问题的最小示例(一些示例数据的 DDL 和 DML 语句 - 即假数据)以及您当前正则表达式如何失败的详细信息。你的问题中有很多不必要的细节,你可以编辑掉。 这似乎是一个XY Problem 如果您只显示数据以及它的假设情况,我们可以为您提供比您执行的那九个步骤更好的解决方案。 【参考方案1】:

Jorge Campos 说这是一个 XY 问题有点正确。

问题最终是我没有包含的一段代码,因为它太简单了,我认为这不是原因。我有一个案例声明,将街道类型的缩写更正为全名,没有其他声明。所以当有一个正确的名字时,它就被取消了,因为只有更正声明。

【讨论】:

以上是关于行没有被正则表达式捕获的主要内容,如果未能解决你的问题,请参考以下文章

Java 正则表达式捕获组索引

如何使用正则表达式仅捕获具有特定格式的有效句子的第一个单词? [复制]

用于在 = 和 ; 之间捕获单词的正则表达式

如何使用正则表达式验证捕获组中的最后一个字符

[javascript] 获取正则子表达式里的内容

正则表达式分组捕获非捕获的示例理解