在Oracle 10g
上,说我有以下专栏:
col
------------------------------------------------------------------------------------------------
[1,98]([1,81]([6,100828],[6,101260]),[1,81]([6,100529],[6,101259]),[1,81]([6,101709],[6,100474]))
我想显示这个结果:
col
------
100828
101260
100529
101259
101709
100474
是否可以使用SQL查询显示此结果?
其实我试过的是:
SELECT SUBSTR(col, INSTR(col, ',', 1, 3) + 1, 6) exp_1,
SUBSTR(col, INSTR(col, ',', 1, 5) + 1, 6) exp_2,
SUBSTR(col, INSTR(col, ',', 1, 8) + 1, 6) exp_3,
SUBSTR(col, INSTR(col, ',', 1, 10) + 1, 6) exp_4,
SUBSTR(col, INSTR(col, ',', 1, 13) + 1, 6) exp_5,
SUBSTR(col, INSTR(col, ',', 1, 15) + 1, 6) exp_6
FROM (SELECT '[1,98]([1,81]([6,100828],[6,101260]),[1,81]([6,100529],[6,101259]),[1,81]([6,101709],[6,100474]))' col
FROM dual) ;
EXP_1 EXP_2 EXP_3 EXP_4 EXP_5 EXP_6
------ ------ ------ ------ ------ ------
100828 101260 100529 101259 101709 100474
但是,返回的exp_%的数量可以是变量,并且总是成对的,这意味着另一行可以返回8 exp_%:
SUBSTR(col, INSTR(col, ',', 1, 18) + 1, 6) exp_7 ,
SUBSTR(col, INSTR(col, ',', 1, 20) + 1, 6) exp_8
修复exp_%的数量的建议也非常受欢迎!
感谢。
答案 0 :(得分:2)
假设您的表名为'foo',列名为'col':
with q as (
select ','||regexp_replace(
regexp_replace(
regexp_replace(
regexp_replace(col, '[[0-9,]*]\(', ''),
'\[[0-9],', ''),
'[])]', ','),
',,+',
',') a from foo
)
select data
from (select substr(a, instr(a, ',', 1, rownum) + 1, 6) data
from q,
(select 1 from q connect by level < length(regexp_replace(a, '[0-9]', '')))
)
;
这是解释。这很快变得复杂,可能无法很好地扩展,所以买家要小心。
首先,我想摆脱'[1,98]('字段。
1 with q as (
2 select
3 regexp_replace(col, '[[0-9,]*]\(', '')
4 from foo
5 )
6* select * from q
REGEXP_REPLACE(COL,'[[0-9,]*]\(','')
------------------------------------------------------------------------------------------------------------------------------------
[6,100828],[6,101260])[6,100529],[6,101259])[6,101709],[6,100474]))
接下来我想摆脱'[n,'部分字段。
1 with q as (
2 select
3 regexp_replace(
4 regexp_replace(col, '[[0-9,]*]\(', ''),
5 '\[[0-9],', ''
6 ) a from foo
7 )
8* select * from q
A
------------------------------------------------------------------------------------------------------------------------------------
100828],101260])100529],101259])101709],100474]))
现在摆脱所有']'和')'
1 with q as (
2 select
3 regexp_replace(
4 regexp_replace(
5 regexp_replace(col, '[[0-9,]*]\(', ''),
6 '\[[0-9],', ''),
7 '[])]', ',')
8 a from foo
9 )
10* select * from q
A
------------------------------------------------------------------------------------------------------------------------------------
100828,,101260,,100529,,101259,,101709,,100474,,,
删除重复的逗号并以逗号开头。
1 with q as (
2 select ','||regexp_replace(
3 regexp_replace(
4 regexp_replace(
5 regexp_replace(col, '[[0-9,]*]\(', ''),
6 '\[[0-9],', ''),
7 '[])]', ','),
8 ',,+',
9 ',') a from foo
10 )
11* select * from q
A
------------------------------------------------------------------------------------------------------------------------------------
,100828,101260,100529,101259,101709,100474,
计算它们的字段数,并为每个字段创建一行。
1 with q as (
2 select ','||regexp_replace(
3 regexp_replace(
4 regexp_replace(
5 regexp_replace(col, '[[0-9,]*]\(', ''),
6 '\[[0-9],', ''),
7 '[])]', ','),
8 ',,+',
9 ',') a from foo
10 )
11* select 1 from q connect by level < length(regexp_replace(a, '[0-9]', ''))
1
----------
1
1
1
1
1
1
1
用q进行笛卡尔连接(注意如果你的表中有多行,这将不起作用。)和一个子字符串来得到你的最终答案。
1 with q as (
2 select ','||regexp_replace(
3 regexp_replace(
4 regexp_replace(
5 regexp_replace(col, '[[0-9,]*]\(', ''),
6 '\[[0-9],', ''),
7 '[])]', ','),
8 ',,+',
9 ',') a from foo
10 )
11 select data
12 from (select substr(a, instr(a, ',', 1, rownum) + 1, 6) data
13 from q,
14 (select 1 from q connect by level < length(regexp_replace(a, '[0-9]', '')))
15* )
DATA
------
100828
101260
100529
101259
101709
100474
6 rows selected.