尝试使用regexp_substr

时间:2017-11-01 17:37:16

标签: sql oracle oracle11g

所以我试图从这个表中解析出具有单个标识符(file_name)的数据,并且有不同的属性,例如first_name,last_name,date_of_birth。这里的问题是其他非标识符列(例如first_name,last_name等)具有通过猜测chr(10)而界定的多个条目。其中一些字段也可以为null(因为DOB如下所示) 例如: 原始数据将包含:filename.xml johnjacob schmidtmiller,1-02-03 我需要它成为: filename.xml john schmidt 1-02-03 filename.xml jacob miller null

我所拥有的内容如下:

    select file_name
          , regexp_substr(first_name, '([^chr(10)]*)(chr(10)|$)', 1, level, null, 1) as first_name
         , regexp_substr(last_name, '([^chr(10)]*)(chr(10)|$)', 1, level, null, 1) as last_name
         , regexp_substr(dob, '([^chr(10)]*)(chr(10)|$)', 1, level, null, 1) as dob
     from TABLE
  connect by level <= regexp_count(first_name, chr(10)) + 1
      and prior file_name = file_name
      and prior sys_guid() is not null
    order by file_name

我目前只返回每个文件名的第一个名字/姓氏/ dob等。我做错了什么?

提前致谢!

1 个答案:

答案 0 :(得分:1)

请查找(谷歌)并阅读REGEXP_SUBSTR功能的文档。您将看到它明确指出,默认情况下,它将LINE的开头和结尾视为整个输入字符串的开头和结尾。可以在第五个参数(现在在代码中为NULL)中覆盖此默认行为。即,将NULL更改为'm'(在对函数的所有调用中)并再次运行。

来自文档:

'm'将源字符串视为多行。 Oracle将^和$分别解释为源字符串中任何位置的任何行的开始和结束,而不是仅在整个源字符串的开头或结尾处。如果省略此参数,Oracle会将源字符串视为单行。

已添加:此外,当我们希望chr(10)代表换行符时,它不应位于带引号的子字符串中。

[^chr(10)]

(在带引号的字符串中)并不表示除LF(换行)之外的任何字符。相反,它表示除了c,h,r,1,0,(和)之外的任何字符。

相反,搜索模式必须使用连接在引用的字符串和CHR(10)OUTSIDE引号之间交替。

'([^chr(10)]*)(chr(10)|$)'
相反,

应该是

'([^'  ||  chr(10)  ||  ']*)('  ||  chr(10)  ||  '|$)'

还要注意,重要的是,我们可以自由(灵活)使用OUTSIDE引用的字符串(为了易读性),但不能在字符串中。例如,插入符号^之后的单引号必须在插入符之后立即显示;如果我们在那里添加一个空格,“为了易读性”,搜索模式将变得不正确。连接运算符||在引用的片段之外,因此我们可以在它们周围添加空格。