我有两个表名table1和table2。
从第一个表我得到number,id和value.ID列是多列表,因此该列中的值用逗号分隔,例如:3799952,3799953。对于每个ID,table2中都有一些值。例如,对于3799952值是汇编,对于3799953值是Indiviual。我必须用逗号分隔来获取这些值。在多列表中,截至目前我只有两个值,所以我使用序列到2,明天我将获得多个值。任何人都可以帮助我程序或用户定义的功能。
select id,item_number,max(decode(seq,1,entry_id))||','||max(decode(seq,2,entry_id)) entry_id,
max(decode(seq,1,entryvalue))||','||max(decode(seq,2,entryvalue)) entryvalue
from (
select a.id,a.item_number,a.entry_id,list.entryvalue,row_number() over (partition by item_number order by entry_id) seq
from (SELECT i.id,i.item_number,
trim(regexp_substr(i.product_lines, '[^,]+', 1, lines.column_value)) entry_id
FROM item i,
TABLE (CAST (MULTISET
(SELECT LEVEL FROM dual CONNECT BY LEVEL <= regexp_count(i.product_lines, ','))AS sys.odciNumberList)) lines ORDER BY i.id)a , listentry list where a.entry_id=list.entryid and a.entry_id is not null)
group by id,item_number;
这是我的查询和输出,如下所示,
**ID ITEM_NUMBER ENTRY_ID ENTRYVALUE**
6024065 P00008 3799953, Individual,
6024607 U00024 3799952,3799953 Assembly,Individual
6024886 U00154 3799952,3799953 Assembly,Individual
6015685 INK_PEN 3799952, Assembly,
6036877 P0000020 3799952,3799953 Assembly,Individual
截至目前,我只有两个入门值,所以使用max(decode(seq,1,entry_id))||','||max(decode(seq,2,entry_id)) entry_id
可以告诉我如何修改多个值。
提前致谢
答案 0 :(得分:0)
您的问题不是很清楚您要实现的目标 - 但是,您似乎有两个逗号分隔的列表要分开,以便值保持相关。您可以使用递归子查询分解子句。像这样(未经测试):
WITH data ( id, item_number, entity_id, entryvalue,
entity_start, entity_end, entry_start, entry_end ) AS (
SELECT id,
item_number,
entity_id,
entryvalue,
1,
INSTR( entity_id, ',', 1 ),
1,
INSTR( entryvalue, ',', 1 )
FROM your_table
UNION ALL
SELECT id,
item_number,
entity_id,
entryvalue,
entity_end + 1,
INSTR( entity_id, ',', entity_end + 1 ),
entry_end + 1,
INSTR( entryvalue, ',', entry_end + 1 )
FROM data
WHERE entity_end > 0 AND entry_start > 0
)
SELECT id,
item_number,
CASE entity_end
WHEN 0
THEN SUBSTR( entity_id, entity_start )
ELSE SUBSTR( entity_id, entity_start, entity_end - entity_start )
END AS entity_id,
CASE entry_end
WHEN 0
THEN SUBSTR( entryvalue, entry_start )
ELSE SUBSTR( entryvalue, entry_start, entry_end - entry_start )
END AS entryvalue
FROM data;
答案 1 :(得分:0)
使用函数listagg()
两次:
select id, item_number,
listagg(entry_id, ',') within group (order by seq) entry_id,
listagg(entryvalue, ',') within group (order by seq) entryvalue
from your_inner_query
group by id, item_number
测试数据:
create table item (id number(8), item_number varchar2(10), product_lines varchar2(20));
insert into item values (6024065, 'P00008', '3799953,');
insert into item values (6024607, 'U00024', '3799952,3799953,');
insert into item values (6024886, 'U00154', '3799952,3799953,');
insert into item values (6015685, 'INK_PEN', '3799952,');
insert into item values (6036877, 'P0000020', '3799952,3799953,');
create table listentry(entryid number(8), entryvalue varchar2(10));
insert into listentry values (3799952, 'Assembly');
insert into listentry values (3799953, 'Individual');
完整查询:
with t as (
select a.id, a.item_number, a.entry_id, list.entryvalue,
row_number() over (partition by item_number order by entry_id) seq
from (select i.id,i.item_number,
trim(regexp_substr(i.product_lines, '[^,]+', 1, lines.column_value)) entry_id
from item i,
table (cast (multiset ( select level
from dual
connect by level <= regexp_count(i.product_lines, ','))
as sys.odcinumberlist)) lines
order by i.id) a
join listentry list on a.entry_id = list.entryid and a.entry_id is not null )
select id, item_number,
listagg(entry_id, ',') within group (order by seq) entry_id,
listagg(entryvalue, ',') within group (order by seq) entryvalue
from t
group by id, item_number
order by id;
输出:
ID ITEM_NUMBER ENTRY_ID ENTRYVALUE
--------- ----------- ------------------ ----------------------
6015685 INK_PEN 3799952 Assembly
6024065 P00008 3799953 Individual
6024607 U00024 3799952,3799953 Assembly,Individual
6024886 U00154 3799952,3799953 Assembly,Individual
6036877 P0000020 3799952,3799953 Assembly,Individual
编辑:解释
子查询a
将表item
中的数据划分为单独的行。分层查询connect by
根据id
中每个,
计数逗号product_lines
生成所需数量的行。
函数regexp_substr
将所需的entry_id
切割为单独的行。
ID ITEM_NUMBER ENTRY_ID
------- ------------ --------
6015685 INK_PEN 3799952
6024065 P00008 3799953
6024607 U00024 3799952
6024607 U00024 3799953
6024886 U00154 3799953
6024886 U00154 3799952
6036877 P0000020 3799952
6036877 P0000020 3799953
这样的表接下来与您的查找表listentry
连接在一起。每行都以row_number()
编号。所以我们有这个:
ID ITEM_NUMBER ENTRY_ID ENTRYVALUE SEQ
------- ------------ -------- ----------- ---
6015685 INK_PEN 3799952 Assembly 1
6036877 P0000020 3799952 Assembly 1
6036877 P0000020 3799953 Individual 2
6024065 P00008 3799953 Individual 1
6024607 U00024 3799952 Assembly 1
6024607 U00024 3799953 Individual 2
6024886 U00154 3799952 Assembly 1
6024886 U00154 3799953 Individual 2
现在我们可以使用listagg()
对相同ID的数据进行分组。它们按SEQ
排序。
请注意,我没有更改您的原始内部查询,仅使用select
而不是listagg()
添加了最后decode
您试过。