Oracle SQL查找字符串&向后工作

时间:2015-01-23 18:50:08

标签: sql oracle

我想做的是在结果中找到一个特定的字符串,然后从该字符串向后工作以获得我需要的东西。举个例子,假设我的结果是“无论如何,这件东西都重500KG”。我想找到“KG”,然后向后工作以获得“500KG”。

我想从KG倒退的原因是结果可能有不同的字符串,如“这件事重500公斤”或“500 - 这件事重500Kg”等唯一不变的是KG(甚至在它变化的状态)。

我正在使用regexp_instr和substr将结果缩小到类似“这件东西重达500KG” - 基本上找到KG并删除它之后的所有内容。

建议?

2 个答案:

答案 0 :(得分:3)

Oracle的正则表达式引擎目前不支持预见或后瞻,因此无法找到您在问题中描述的正确字符串的过程。

话虽如此,你可以使用REGEXP_SUBSTR()来做到这一点;以下内容可能会起作用(取决于您的数据):

regexp_substr(str, '\d+\s?kg', 1, 1, 'i')

搜索任意数量的数字,后跟可选空格,后跟字符串kg。其他参数是位置(从1开始),出现(第一个)和匹配参数(不区分大小写)。

这可以满足您的需求:

SQL> with str (s) as (
  2  select 'This thing is heavy at 500 kg'
  3    from dual
  4   union all
  5  select '500 - This thing is heavy 500Kg'
  6    from dual
  7         )
  8  select regexp_substr(s, '\d+\s?kg', 1, 1, 'i')
  9    from str;

REGEXP_SUBSTR(S,'\D+\S?KG',1,1,'I')
---------------------------------------------------
500 kg
500Kg

SQL>

这是有效的,因为您正在kg搜索跟随的数字。因此,如果此字符串后面没有数字,则不会返回。

根据您的数据和您想要的输出,这可能还不够。例如,如果千克也可以表示为k.g.,并且您想要删除数字和大写之间的空格,那么您可能希望执行以下操作:

SQL> with str (s) as (
  2  select 'This thing is heavy at 6872 kg'
  3    from dual
  4   union all
  5  select '157 - This thing is heavy 248K.g'
  6    from dual
  7         )
  8  select regexp_substr(s, '(\d+)\s?k\.?g', 1, 1, 'i', 1) || 'KG'
  9    from str;

REGEXP_SUBSTR(S,'(\D+)\S?K\.?G',1,1,'I',1)||'KG'
-------------------------------------------------------------------
6872KG
248KG

SQL>

我添加的最后一个参数是要返回的子表达式,由组(\d+)标识。这将选出第一个(唯一的)子表达式,它将是您的数字,并将字符串KG连接到该数字的末尾。

答案 1 :(得分:0)

如果您使用的是Oracle 10g,则可以执行以下操作(@ Ben的答案可以在11g或12c中正常运行):

SELECT REGEXP_REPLACE(mystring, '^.*?(\d+)\s*k\.?g.*$', '\1KG', 1, 1, 'i')
  FROM mytable

这里我们不能使用REGEXP_SUBSTR()的原因是最终参数(subexpression)在此函数的10g版本中不存在。

如果你想捕捉各种测量单位,那可能会更困难,但仍然不是不可能,例如:

SELECT REGEXP_REPLACE(mystring, '^.*?(\d+)\s*(k?g|lbs?|oz).*$', '\1\2', 1, 1, 'i')
  FROM mytable

这会捕获克(g),千克(kg),磅(lblbs)和盎司(oz)。