在2列中拆分特殊字符,并在oracle

时间:2019-02-07 19:37:51

标签: sql oracle plsql

很高兴认识你们。我有一个名为A的表。该表包含名为col1和col2的两列。具有TN ^ AN ^ KA ^之类数据的col1和col2包含123 ^ 456 ^ 987。

需要删除^字符并将两个列值合并为多个行,如下所示。

DDL:

Create table a (col1 varchar2(20), col2 varchar2(20));

DML:

insert into values ('TN^AN^KA','123^456^987');
commit;

select * from a;
----------     --------------
col1          col2 
---------     ---------------
TN^AN^KA       123^456^987

需要这样的输出

TN123

AN456

KA987

5 个答案:

答案 0 :(得分:0)

因此,您有2个列,仅包含值TN^AN^KA123^456^987。可以使用substr()

  select substr(A.col1,1,2)||substr(A.col2,1,3) from table A
  union all
  select substr(A.col1,4,2)||substr(A.col2,5,3) from table A
  union all
  select substr(A.col1,7,2)||substr(A.col2,9,3) from table A

Result:

答案 1 :(得分:0)

这里是一个解决方案,允许每个输入字符串中包含任意数量的部分(两列中不一定相同,并且从一行到另一行可变)。两个连续的插入符号表示该令牌为NULL。我添加了一个ID(因此您将知道每个输出字符串的来源),并且添加了ORD列以显示第一个令牌与第二个令牌,第三个令牌等。

在查询中,我使用LATERAL子句(自Oracle 12.1起可用),该子句使我们能够与其他行分开地独立处理每个输入行,这使查询更快,更简单。在正则表达式中,请注意,字符集(此处为否定字符集)中的 except 必须转义插入符号(否则表示“字符串开头”),其中元符号失去其特殊含义。

新设置

drop table a purge;
Create table a (id number, col1 varchar2(20), col2 varchar2(20));
insert into a values (101, 'TN^AN^KA','123^456^987');
insert into a values (102, 'AB^CE^YZZ', '234^000');
insert into a values (103, 'AB', '0230');
commit;

查询和输出

select a.id, l.ord, l.token
from   a,
       lateral (select  level as ord,
                        regexp_substr(col1, '([^^]*)(\^|$)', 1, level, null, 1) ||
                        regexp_substr(col2, '([^^]*)(\^|$)', 1, level, null, 1)
                        as token
                from    dual
                connect by level <= 1 + greatest(regexp_count(col1, '\^'),
                                                 regexp_count(col2, '\^'))
               ) l
order by id, ord;

   ID ORD TOKEN   
----- --- --------
  101   1 TN123   
  101   2 AN456   
  101   3 KA987   
  102   1 AB234   
  102   2 CE000   
  102   3 YZZ     
  103   1 AB0230 

答案 2 :(得分:0)

REGEXP_SUBSTR怎么样?我略微修改了输入数据,以便不会统一设置返回值。它有什么作用?在^个字符之间输入个单词。如果分隔符更改,则此代码可能(也可能不会)起作用。

SQL> with test (col1, col2) as
  2    (select 'TN^AN^KA', '123^45^6789' from dual)
  3  select regexp_substr(col1, '\w+', 1, 1) || regexp_substr(col2, '\w+', 1, 1) res1,
  4         regexp_substr(col1, '\w+', 1, 2) || regexp_substr(col2, '\w+', 1, 2) res2,
  5         regexp_substr(col1, '\w+', 1, 3) || regexp_substr(col2, '\w+', 1, 3) res3
  6  from test;

RES1  RES2 RES3
----- ---- ------
TN123 AN45 KA6789

SQL>

答案 3 :(得分:0)

您可以同时使用regexp_substrregexp_countconcat

  with a(col1, col2) as
  (
    select 'TN^AN^KA','123^456^987' from dual
  )
    select concat(
                  regexp_substr(col1, '[^\^]+', 1, level),
                  regexp_substr(col2, '[^\^]+', 1, level) 
                 ) as "Result String"  
      from a
    connect by level <= regexp_count(col1, '\^') + 1;

 Result String
 -------------
 TN123
 AN456
 KA987

Demo

答案 4 :(得分:0)

使用regexp_substr获得所需的结果。

func retriveInfo() {

    let databaseRef = Database.database().reference().child("User_Informations")


        databaseRef.observeSingleEvent(of: .value, with: { (snapshot) in

            for snap in snapshot.children {
                let userSnap = snap as! DataSnapshot
                let uid = userSnap.key //the uid of each user
                let userDict = userSnap.value as! [String:AnyObject] //child data
                let firstName = userDict["firstName"] as! String
                let lastName = userDict["lastName"] as! String

                print("key = \(uid) First Name = \(firstName), Last Name = \(lastName)")
            }
        })