用sql loader中另一列的子字符串替换一列的数据

时间:2016-03-02 06:50:00

标签: oracle csv sql-loader

我正在使用sqlldr将csv文件中的数据加载到表中。 csv文件的每一行都有一列不存在。填充此列所需的数据存在于该行的其他列之一中。我需要拆分(拆分(。))该列的数据并填充到该列中。

如: -

 column1:- abc.xyz.n  

所以未知列(column2)应该是

 column2:- xyz

此外,行中还有另一列,但它不是我想要输入到表中的列。它还需要从column1填充。但是那里有大约50个if-else案例。解码比这更好吗?

column1:- abc.xyz.n

然后,

column2:- hi if(column1 has 'abc')
             if(column1 has 'abd' then 'hello')
像这样,大约有50个if-else案例。

感谢您的帮助。

1 个答案:

答案 0 :(得分:2)

对于问题的第一部分,将控制文件中的column1数据定义为BOUNDFILLER,其名称与表列名称不匹配,告诉sqlldr记住它但不使用它。如果需要将其加载到列中,请使用列名称和记住的名称。对于column2,在表达式中使用记住的BOUNDFILLER名称,它返回所需的部分(在本例中为第二个字段,允许NULL):

  x        boundfiller,
  column1  EXPRESSION  ":x",
  column2  EXPRESSION  "REGEXP_SUBSTR(:x, '(.*?)(\\.|$)', 1, 2, NULL, 1)"

请注意,需要使用双反斜杠,否则当它从sqlldr传递到正则表达式引擎时会被删除,并且正则表达式模式会被错误地更改。我想是一个怪癖。

无论如何,在此列1结束后," abc.xyz.n"和column2得到" xyz"。

对于问题的第二部分,您可以使用已经显示的表达式,但调用您创建的自定义函数,其中您传递提取的值,它将从查找表返回搜索的值。您当然不想对50个查找值进行硬编码。您也可以在表级触发器中执行相同的操作。注意我只为一个示例显示了一个select语句,但是这应该封装在一个可重用性和可维护性的函数中:

只是为了表明你可以做到:

 col2  EXPRESSION  "(select 'hello' from dual where REGEXP_SUBSTR(:x, '(.*?)(\\.|$)', 1, 2, NULL, 1) = 'xyz')"

正确的方式:

 col2  EXPRESSION  "(myschema.mylookupfunc(REGEXP_SUBSTR(:x, '(.*?)(\\.|$)', 1, 2, NULL, 1)))"

mylookupfunc返回查找结果' xyz'在查找表中,即'你好'按照你的例子。