首页 > 解决方案 > 我正在尝试做的是获得每个项目过去一年中每一天的运行库存水平

问题描述

我有下面的 SQL 查询,但它很慢。运行查询大约需要 1 分钟。这将被制成一个存储过程。这不是问题。但是对于大约有 600 个项目的每个项目都会调用该存储过程。估计的运行时间可能最终需要大约 10 个小时。有没有人有更好的方法建议?

我想要做的是获得每个项目过去一年中每一天的运行库存水平。

如果您需要更多信息。请告诉我。

DECLARE @StartDate AS DATETIME
DECLARE @EndDate AS DATETIME
DECLARE @CurrentDate AS DATETIME
DECLARE @ItemName As Varchar(450)
DECLARE @QOH DECIMAL(19,4)

SET @QOH = 0
SET @ItemName = 'TUR001-02'
SET @StartDate = '2020-04-01'
SET @EndDate = GETDATE()
SET @CurrentDate = @StartDate

CREATE TABLE #TempTable
(
    Date datetime,
    ItemName char(450),
    QOH DECIMAL(19,4) 
);

WHILE (@CurrentDate < @EndDate)
BEGIN
    DECLARE @daySales DECIMAL(19,4)
    
    SELECT @daySales = SUM(Quantity) 
    FROM qbInvoiceLineDetail 
    WHERE TxnDate = @CurrentDate AND FullName = @ItemName;

    SET @QOH = @QOH - @daySales 

    INSERT INTO #TempTable (Date, ItemName, QOH) 
        SELECT @CurrentDate, @ItemName, @QOH;

    SET @CurrentDate = DATEADD(DAY, 1, @CurrentDate); 
END

SELECT * FROM #TempTable

DROP TABLE #TempTable

标签: sqlsql-serverazure-sql-database

解决方案


您可以使用 atally table在开始和结束之间生成日期,然后将所有数据一次性插入表中。

警告 - 这是未经测试的,因为我没有什么可以检查的,假设日期只是日期,如果它们包括time然后将需要使用convert- 希望将是你正在寻找的:

/*first, create a tally table - this should be a permanent feature */

select top 1000 N=Identity(int, 0, 1)
into dbo.Digits
from master.dbo.syscolumns a cross join master.dbo.syscolumns


declare @StartDate datetime='20200401', @EndDate datetime=GetDate()

select DateAdd(day,N,@startDate) currentDate, FullName ItemName, Sum(Quantity) over(order by d.N) QOH
from Digits d
left join qbInvoiceLineDetail  q on q.TxnDate=DateAdd(day,N,@startDate)
where DateAdd(day,N,@startDate)<=@EndDate
group by TxnDate, ItemName

推荐阅读