我有一个只返回一条记录的SQL存储过程。但是,在该proc中,是一个子查询,可以返回多行。我认为最好设计子查询以返回多行的一行,而不是多行。
如何写出子查询以便返回列 目前查询是:
SET @Pkg_Status = (Select lf.name, edi.Date from EdiPackage edi, Labelfeed lf
Where edi.orderID = @OrderID
AND edi.code = lf.code
AND lf.labelID = 'EDIStage')
上述查询的示例结果集将为:
Column 1 Column 2 Field1.Value1 Field2.Value1 Field1.Value2 Field2.Value2 Field1.Value3 Field2.Value3
相反,我希望结果是:
Column 1 | Column2 | Column3 | Column4 | Column 5 | Column 6 Field1.Value1 | Field2.Value1 | Field1.Value2 | Field2.Value2 | Field1.Value3 | Field2.Value3
如何做到这一点?
答案 0 :(得分:4)
首先,在连接两个表时应使用ISO Join关键字,而不是通过逗号分隔表,然后在Where子句中“连接”它们。所以我们的查询是:
Select LF.name, EDI.Date
From EdiPackage As EDI
Join LabelFeed As LF
On LF.Code = EDI.Code
Where EDI.orderID = @OrderID
And LF.labelID = 'EDIStage'
其次,您的原始示例是将查询结果设置为变量。这不适用于多列或多行。最好的情况是,SQL可能只是占用子查询中的第一列。最后,你听起来像是一个交叉的东西。我们需要查看数据,但您可以通过这样做来实现您想要的目标:
Select Min( Case When LF.Name = 'Value1' Then LF.Name End ) As Col1
, Min( Case When LF.Name = 'Value1' Then EDI.Date End ) As Col2
, Min( Case When LF.Name = 'Value2' Then LF.Name End ) As Col3
, Min( Case When LF.Name = 'Value2' Then EDI.Date End ) As Col4
, Min( Case When LF.Name = 'Value3' Then LF.Name End ) As Col5
, Min( Case When LF.Name = 'Value3' Then EDI.Date End ) As Col6
From EdiPackage As EDI
Join LabelFeed As LF
On LF.Code = EDI.Code
Where EDI.orderID = @OrderID
And LF.labelID = 'EDIStage'
在这种情况下,您可以将'Value1','Value2'和'Value3'替换为应该用于区分一列与另一列的数据值。
答案 1 :(得分:0)
您应该编写一个存储过程,该存储过程将创建一个新的内存表,您可以动态地向其添加列,并且每列将具有不同的行。
答案 2 :(得分:0)
在SQL 2005及更高版本中,您将使用pivot。
如果列数已修复,请使用Thomas给出的答案。
否则,要将它们压成一个区域,你会做类似
的事情Declare @Pkg_Status Character Varying(8000)
Select @Pkg_Status =
Coalesce(@Pkg_Status + ',' + LF.Name + ',' + Cast(EDI.Date As Character Varying),
LF.Name + ',' + Cast(EDI.Date As Character Varying))
From
dbo.EDIPackage As EDI
Inner Join dbo.LabelFeed As LF
On EDI.Code = LF.Code
Where
(EDI.OrderID = @OrderID)
And (LF.LabelID = 'EDIStage')