1

你知道是否可以将这样的模式转换为正则表达式:

ABCDXXXXYYYY

其中 ABCDEFGH.. 是连续数字,V、X、Y、Z 是任意数字。

上面的模式应该匹配:

123400006666 456799994444等

请注意,我不是要求一个完整的解决方案,而是关于如何解决这个问题的一些想法。您以前是否遇到过这样的情况(在数据库中搜索似乎不适合 RegExps 的已定义模式?

任何评论将不胜感激。

4

2 回答 2

3

您无法识别正则表达式中的连续数字,因为它们过于依赖上下文。

但是,我认为这在 PL/SQL 中很容易实现,并且在 SQL 中也可能实现。

如果您只想connect by使用 SQL,那么您可以使用未记录函数wm_contact或用户定义函数的组合生成一串连续数字stragg

就像是:

 select replace(stragg(level),',','')
   from dual
connect by level <= 5

将它与正则表达式连接可能会让你接近,但我不认为这是要走的路。我肯定会使用 PL/SQL 函数进行调查,并可能完全忘记正则表达式。

执行以下操作会将一个数字拆分为一个数组,然后您可以循环并对其进行操作。根据要求,这只是一个起点,您可能希望对其进行大量更改。由于没有实际的 SQL,它只是字符串操作,因此执行此类操作非常有效。

create or replace function validate_phone( P_phone number ) 
                 return number is

   type t__phone is table of number index by binary_integer;
   t_phone t__phone;

   l_consecutive varchar2(150);

begin

   -- Test whether we actually have a number first ( code below ).
   if is_number(P_phone) = 0 then
       return null;
   end if;

   -- Split out the phone number into individual array elements.
   for i in 1 .. length(to_char(P_phone)) loop

      t_phone(i) := substr(to_char(P_phone, i, 1))

   end loop;

   for i in t_phone.first .. t_phone.last loop

      -- If we find a consecutive number then build this string.
      if t_phone.exists(i + 1)
        and t_phone(i) = t_phone(i + 1) - 1 then
         l_consecutive := l_consecutive || t_phone(i);
      end if;

   end loop;

   return something;

end validate_phone;

如上所示,您可能首先要检查您的电话号码是否实际上是数字:

create or replace function is_number( P_number varchar2 ) 
        return number is

   /* Test a number to see whether it actually is one
      return a 1 / 0 rather than boolean so it can also
      be used in plain SQL.
      */

   l_number number;

begin

   l_number := P_number;

   return 1;

exception when others then
   return 0;
end is_number;
于 2012-05-05T11:04:59.320 回答
2

您描述的语言不是上下文无关的(如果由连续数字组成的前缀长度是任意的)并且不是正则语言,因此不能用正则表达式表示。

于 2012-05-05T10:34:24.567 回答