2015-10-13 103 views
1

我有一个像逗号分隔的字符串成列的Oracle分裂

Charge_num  mapping_col 
---------  ----------- 
p1.pm.100  1.1.1,1000 
p1.pm.110  1.2.1,1000 
p1.pm.120  1.3.1,1000 

一个表,我需要的“mapping_col”分成两列是这样的:

Charge_num  wbs  obs 
---------  ---  --- 
p1.pm.100  1.1.1  1000 
p1.pm.110  1.2.1  1000 
p1.pm.120  1.3.1  1000 
+0

首先,为什么要将数据存储为分隔字符串?你正在违反**正常化**。无论如何,作为一种解决方法,只需使用'SUBSTR'和'INSTR'。 INSTR将返回逗号','的位置,然后根据该位置分开substr。请记住,即使使用12c,SUBSTR + INSTR方法仍然比REGEX更快。 –

+0

我没有这样保存,但我必须编写一份报告,从该系统中提取数据。当我第一次发现这种情况时,我的第一次呼吁是它违反了第一种正常形式。 – user2378895

+0

“*它违反了第一范式*”当然这违反了基本规则。无论如何,我想,你现在可以应用这个解决方法。并且,提出一个设计修正作为您的组织的永久解决方案。你甚至可以创建**虚拟列**。祝你好运! –

回答

1
select charge_num, 
substr(mapping_col,1,instr(mapping_col,',',1)-1) AS first_half, 
substr(mapping_col, instr(mapping_col,',',1)+1) as last_half 
from your_table 

注意,实践将数字存储为字符串很容易出错。如果您将这些结果视为NUMBER(9),那么如果您的数据不规则,可能会发生意外破裂

+1

@感谢您的支持,更正... – kevinsky

+0

“*请注意,将数字存储为字符串的做法很容易出错。如果您要将这些结果作为NUMBER(9)进行投射,那么如果数据不规则*那么,我确实同意你的观点。但是,也有例外。请注意,很多国家都遵循其数据的某些规范,因此您必须将数据存储为分隔字符串。 –

1

REGEXP_SUBSTR要拯救!

with sample_data as (select 'p1.pm.100' charge_num, '1.1.1,1000' mapping_col from dual union all 
        select 'p1.pm.110' charge_num, '1.2.1,1000' mapping_col from dual union all 
        select 'p1.pm.120' charge_num, '1.3.1,1000' mapping_col from dual) 
select charge_num, 
     regexp_substr(mapping_col, '[^,]+', 1, 1) wbs, 
     regexp_substr(mapping_col, '[^,]+', 1, 2) obs 
from sample_data; 

CHARGE_NUM WBS       OBS       
---------- ------------------------------ ------------------------------ 
p1.pm.100 1.1.1       1000       
p1.pm.110 1.2.1       1000       
p1.pm.120 1.3.1       1000   
+0

每个新版本的正则表达式的性能显然会越来越好。 +1 –