如何在SP中对查询进行别名并在整个过程中使用结果

时间:2012-03-27 05:39:24

标签: sql-server tsql stored-procedures

编写一个存储过程,其中我有4个选择查询

我希望第一个选择查询中的一些数据用于其余三个查询的where子句中。

SELECT TOP 100 * FROM dbo.[Order] WHERE (dbo.[Order].[CreatedOn]<(GetDate()-7)) AND ((@OrderId IS NULL)OR(dbo.[Order].[OrderId] BETWEEN (@OrderId) AND (@orderId+100))) ORDER BY dbo.[Order].[OrderId]

SELECT * FROM dbo.[OrderItem] WHERE  dbo.[OrderItem].[OrderId] IN(SELECT TOP 100 dbo.[Order].[OrderId] FROM dbo.[Order] WHERE (dbo.[Order].[CreatedOn]<(GetDate()-7)) AND ((@OrderId IS NULL)OR(dbo.[Order].[OrderId] BETWEEN (@OrderId) AND (@orderId+100))))

SELECT  dbo.OrderItemAddOn.* FROM dbo.OrderItemAddOn INNER JOIN dbo.MenuItemAddOn ON dbo.OrderItemAddOn.MenuItemAddOnId = dbo.MenuItemAddOn.MenuItemAddOnId           
   INNER JOIN dbo.MenuAddOn ON dbo.MenuItemAddOn.MenuAddOnId = dbo.MenuAddOn.MenuAddOnId          
   INNER JOIN dbo.OrderItem ON dbo.OrderItemAddOn.OrderItemId = dbo.OrderItem.OrderItemId  
   AND dbo.OrderItem.OrderId IN(SELECT TOP 100 dbo.[Order].[OrderId] FROM dbo.[Order] WHERE (dbo.[Order].[CreatedOn]<(GetDate()-7)) AND ((@OrderId IS NULL)OR(dbo.[Order].[OrderId] BETWEEN (@OrderId) AND (@orderId+100)))) ORDER BY dbo.OrderItemAddOn.OrderItemAddOnId, dbo.OrderItemAddOn.OrderItemId            

SELECT DISTINCT * FROM    dbo.OrderItemModifier INNER JOIN dbo.OrderItem ON dbo.OrderItemModifier.OrderItemId = dbo.OrderItem.OrderItemId 
    AND dbo.OrderItem.OrderId IN (SELECT TOP 100 dbo.[Order].[OrderId] FROM dbo.[Order] WHERE (dbo.[Order].[CreatedOn]<(GetDate()-7)) AND ((@OrderId IS NULL)OR(dbo.[Order].[OrderId] BETWEEN (@OrderId) AND (@orderId+100))))          
    LEFT OUTER JOIN dbo.MenuModifierGroup ON dbo.OrderItemModifier.MenuModifierGroupId = dbo.MenuModifierGroup.MenuModifierGroupId ORDER BY OrderItemModifier.OrderItemId

如果您注意到此查询

SELECT OrderId FROM dbo.[Order] WHERE (dbo.[Order].[CreatedOn]<(GetDate()-7)) AND ((@OrderId IS NULL)OR(dbo.[Order].[OrderId] BETWEEN (@OrderId) AND (@orderId+100))) ORDER BY dbo.[Order].[OrderId]

正在重复,因为我想要来自此查询的OrderIds。上面的查询肯定是错误的方法..我想别名这个查询,并希望在我的所有查询中使用相同的结果..你们可以请帮助。

我们能做的是别名这个查询并在所有四个查询中使用相同的结果..这也是一个很好的解决方案......但是如何在SP中对查询进行别名..

3 个答案:

答案 0 :(得分:2)

您可以研究一些选项:

  • 临时表
  • 表值变量
  • 查看
  • 公用表表达式
  • 返回表的UDF或存储过程

虽然我不能从你提供的查询中对你的案例说太多,但一个简单的起点是使用名为#recent_orders的临时表来保存子查询的结果:

SELECT TOP 100 * FROM dbo.[Order] 
INTO #recent_orders
WHERE (dbo.[Order].[CreatedOn]<(GetDate()-7)) 
AND (
   (@OrderId IS NULL)
    OR
   (dbo.[Order].[OrderId] BETWEEN (@OrderId) AND (@orderId+100))
) 
ORDER BY dbo.[Order].[OrderId]

然后,您可以在后续查询中引用它,如下所示:

SELECT * FROM dbo.[OrderItem]
WHERE  dbo.[OrderItem].[OrderId] IN(SELECT [OrderId] FROM #recent_orders)

答案 1 :(得分:0)

select column_1 into #tmp_first_result
from FIRST_QUERY WHERE ....


select *
from SECOND_QUERY INNER JOIN #tmp_first_result T ON (......)

您可以将#tmp_first_result重复用于任何其他查询。

答案 2 :(得分:0)

如果您想要别名的查询用于不同的存储过程,则其中一种解决方案是使用Inline Table-Valued Functions。在你的情况下:

CREATE GetOrderID(@Date Date, @OrderId INT)
RETURNS TABLE
AS
RETURN (
SELECT OrderId FROM dbo.[Order] WHERE (dbo.[Order].[CreatedOn]<(@Date-7)) AND ((@OrderId IS NULL)OR(dbo.[Order].[OrderId] BETWEEN (@OrderId) AND (@orderId+100))) ORDER BY dbo.[Order].[OrderId]
)

现在您可以使用此功能(例如,您的查询的最后一个):

SELECT DISTINCT * FROM    dbo.OrderItemModifier INNER JOIN dbo.OrderItem ON dbo.OrderItemModifier.OrderItemId = dbo.OrderItem.OrderItemId 
    AND dbo.OrderItem.OrderId IN (SELECT TOP 100 FROM dbo.GetOrderID(GetDate(), @OrderID))          
    LEFT OUTER JOIN dbo.MenuModifierGroup ON dbo.OrderItemModifier.MenuModifierGroupId = dbo.MenuModifierGroup.MenuModifierGroupId ORDER BY OrderItemModifier.OrderItemId

抱歉,我没有测试过这段代码,仅举例来说。