我有一张扁平的,非规范化的表格:
PRODUCT_ID LOCATION PARTNUMBER PRICE STATUS
1234567890 9999 5555 10.99 A
1234567890 8888 5555 11.99 A
1234567890 7777 5555 9.99 B
9876543210 9999 3333 15.99 A
9876543210 4444 3333 14.99 A
...
我需要查询它以生成一个如下所示的输出文件:
1234567890|9999|5555|10.99|A,8888|5555|11.99|A,7777|5555|9.99|B
9876543210|9999|3333|15.99|A,4444|3333|14.99|A
...
所以基本上是一种数据格式:
PRODUCT_ID | LOCATION1 | PARTNUMBER1 |价格1 | STATUS1,LOCATIONN | PARTNUMBERN | PRICEN,STATUSN,...
我不确定从哪里开始....我应该使用嵌套查询吗?
答案 0 :(得分:0)
你需要创建一个游标来遍历你的表。 使用变量来控制表的每一行是否引用相同的产品或新产品。
这样的事情:
DECLARE @OLD_PRODUCT_ID int
set @OLD_PRODUCT_ID = -1
DECLARE MyCursor CURSOR FOR
select PRODUCT_ID, LOCATION, PARTNUMBER, PRICE, STATUS
FROM YourTable
OPEN MyCursor;
FETCH NEXT FROM MyCursor
INTO @PRODUCT_ID, @LOCATION, @PARTNUMBER, @PRICE, @STATUS --declare these variables
WHILE @@FETCH_STATUS = 0 BEGIN
if (@PRODUCT_ID = @OLD_PRODUCT_ID) begin
-- use the same line
end ele begin
-- new product = new line
end
@OLD_PRODUCT_ID = @PRODUCT_ID
FETCH NEXT FROM MyCursor
INTO @PRODUCT_ID, @LOCATION, @PARTNUMBER, @PRICE, @STATUS
END
CLOSE MyCursor;
DEALLOCATE MyCursor;
答案 1 :(得分:0)
还有一些方法可以实现这个w / o循环,但是sql更难。
地点列表是否有限且很小?
如果是这样,你可以这样做:
select a.product_id ||
coalesce((select '|' || b.location || '|' || b.partnumber || '|' ||
b.price || '|' || trim(b.status) || ','
from session.products b
where b.location = '9999' and b.product_id = a.product_id), '') ||
coalesce((select '|' || c.location || '|' || c.partnumber || '|' ||
c.price || '|' || trim(c.status) || ','
from session.products c
where c.location = '8888' and c.product_id = a.product_id), '')
from (select distinct product_id as product_id from session.products) as a
您为每个位置扩展语句。
有一些方法可以在sql中为一组无限制的位置执行此操作,但是读取/写入/调试并不容易,并且+ Diego的光标解决方案可能更合适。
答案 2 :(得分:0)
有趣的是,你可以递归地说:
WITH Ordered_Data (product_id, orderIndex, dataString) as (
SELECT product_id, location, partnumber, price, status,
ROW_NUMBER() OVER(PARTITION_BY product_id ORDER BY product_id, location ASC),
product_id || '|' || location || '|' || partnumber || '|' ||
price || '|' || status
FROM Product_Location),
Combined_Data(product_id, orderIndex, dataString) as (
SELECT a.product_id, a.orderIndex, a.dataString
FROM Ordered_Data as a
JOIN (SELECT product_id, MAX(orderIndex) as orderIndex
FROM Ordered_Data
GROUP BY product_id) as b
ON b.product_id = a.product_id
AND b.orderIndex = a.orderIndex
UNION ALL
SELECT b.product_id, a.orderIndex, b.dataString || ',' || a.dataString
FROM Ordered_Data as a
JOIN Combined_Data as b
ON b.product_id = a.product_id
AND b.orderIndex - 1 = a.orderIndex)
SELECT dataString
FROM Combined_Data
WHERE orderIndex = 1
产生预期的结果:
9876543210|9999|3333|15.99|A,9876543210|4444|3333|14.99|A
1234567890|9999|5555|10.99|A,1234567890|8888|5555|11.99|A,1234567890|7777|5555|9.99|B
我不保证 fast 如何运行 - 特别是,你需要一个索引(product_id
,location
)(或类似的,并调整声明)。我相信DB2足够聪明,可以向后读取指标,所以方向并不重要。
作为旁注,我真的希望price
是numeric
或decimal
(精确小数),而不是float
或{{ 1}}。