【问题标题】:To check if specified pattern is repeating through the entire length of string检查指定的模式是否在整个字符串长度中重复
【发布时间】:2016-12-07 16:34:57
【问题描述】:

我正在尝试匹配类似于“12345@5.6;12345@45;12345@0.5”的模式。我正在尝试使用 Oracle(11g) REGEXP_LIKE 函数来做到这一点。 这是我的代码-

设置服务器输出;

开始

if regexp_like(TRIM('12345@5.6;12345@45;12345@0.5'),'[^\d+@((\d+.\d{0,4})|(\d+));$ ]+')

then
dbms_output.put_line('yes');
else 
dbms_output.put_line('No');
end if;

结束;

对于上面的代码输出是“是”,这是我想要的。但是对于 '12345@5.6,12345@45;12345@0.5' 等模式,此代码也返回“是” (而不是分号,我在 '5.6' 之后指定了逗号)。

它基本上是在检查模式,但如果它发现至少一种这种模式,则返回 true,而不是检查剩余的字符串以确保所有内容都在模式中。

我只想要字符串的整个长度中指定类型的模式。如果某些内容超出模式,我需要返回“否”。

另一个例子:- 假设有一个字符串 'abc;abc;abc' 我想检查模式 'abc' 是否不仅存在于字符串中,而且还在整个字符串中重复。 这意味着代码应该为像 'abc;bca;def' 这样的字符串返回 false 并且应该只为 'abc;abc;abc' 返回 true。

需要明确的是,我只是想检查指定的模式是否在整个字符串长度中重复,否则我想返回“否”,而不仅仅是看到至少一个存在并返回 true,我不知道多少次这种模式存在。

希望我清楚,请帮助。谢谢。

【问题讨论】:

  • 你的描述真的不是很清楚。试试'^[0-9]+@[0-9]+(\.[0-9]{0,4})?(;[0-9]+@[0-9]+(\.[0-9]{0,4})?)+$'。如果它对你有用,我会发布解释。见here how it works
  • 我在您的第一个示例中看不到重复模式。您需要对“模式”和“匹配”给出更精确的定义。
  • @Tejaduggirala - 好吧,这更有意义。我假设“数字”是指非负数(不允许减号),并且它必须以 10 为底(没有十六进制数,没有使用指数的科学记数法)。小数怎么样......是否允许 0.33,或者在这种情况下它必须是 0.33?另外,1. 是否允许(整数 1)? Oracle 允许将 0.33 和 1. 作为数字 - 您的业务需要吗?
  • @mathguy 我想要在字符串中的模式是(number@number 或十进制;)比如 '12456@45;12345@4.3;'或 '12345@45;5432@3.2;6785@34' 结尾可以是分号或不带分号。我的问题是,在字符串 '12345@34,34567@4.5;45678@22' 上使用 REGEXP_LIKE 时,我的正则表达式返回 true ,因为在 '34' 之后它有 ',' 而不是 ';'但我的正则表达式返回真,因为在这个字符串 '12345@34,34567@4.5;45678@22', '34567@4.5;'匹配我的表达式。我需要我的正则表达式匹配,只有当字符串重复'somenumber@somenumber or decimal;'
  • 这个问题很简单(为什么你的代码不起作用)。有几个问题;导致直接错误结果的一个是使用[ ... | ... ],您可能指的是( ... | ... ) 进行交替。 [...] 用于匹配方括号内的任何字符。

标签: oracle11g pattern-matching regexp-like


【解决方案1】:

你可以使用

'^[0-9]+@[0-9]+(\.[0-9]{0,4})?(;[0-9]+@[0-9]+(\.[0-9]{0,4})?‌​)+$'

regex demo

您在此正则表达式中的主要构建块是 [0-9]+@[0-9]+(\.[0-9]{0,4})? - 一位或多位数字、@、1+ 位数字,然后是一个 可选(请参阅带有 @ 的 (...)? 分组结构987654326@ 匹配 1 次或 0 次出现的量词)点序列 (\.) 和 0 到 4 位数字 ([0-9]{0,4} - 如果您不想允许之后没有数字的点,请将 0 替换为 @987654330 @)。

然后,您要验证由这些块组成的 整个 字符串,并以分号作为分隔符。你需要使用

      ^    +   block   + (      ;    + block  +  )       +         $
      |                  |      |                |       |         |
    string             group   sep             group 1 or more   string 
    start              start                    end  occurrences  end

【讨论】:

    【解决方案2】:

    我认为这应该可行:

    with
         inputs ( str ) as (
           select '12345@5.6;12345@45;12345@0.5' from dual union all
           select '12345@5.6;12345@45,12345@0.5' from dual
         )
    select str,
           case when regexp_like(str, '^(\d+@(\d+|\d*.\d+)(;|$))+$') then 'valid'
                else 'invalid' end
           as   result
    from   inputs
    ;
    
    
    STR                           RESULT
    ----------------------------  -------
    12345@5.6;12345@45;12345@0.5  valid
    12345@5.6;12345@45,12345@0.5  invalid
    

    开头的^ 和结尾的$ 保证必须匹配整个字符串(不是它的任何子字符串,而是它的全部)。匹配模式中的倒数第二个字符+ 需要“模式”的一个或多个重复。您了解\d+@ 部分。然后有两种选择 - 允许整数或小数,并以分号或字符串结尾结束。

    这不允许像 3. 这样的东西作为模式的“第二部分”。此外,如果您的“第二部分”是一个 IP 地址,通常有四个部分,而不是两个部分,则需要调整匹配模式。如果您需要帮助,请回信。

    【讨论】:

      猜你喜欢
      • 1970-01-01
      • 2018-05-24
      • 2012-09-14
      • 1970-01-01
      • 2016-02-18
      • 2019-09-14
      • 2018-09-25
      • 2014-03-03
      • 1970-01-01
      相关资源
      最近更新 更多