编辑:DB是SQL Server 2008R2
所以,本质上,我遇到了一个问题,其中#行!= count(*)。运行此代码:
SELECT *
FROM Fn_ForecastReport_TEST(NULL)
返回519行输出。但是,运行以下代码:
SELECT COUNT(*)
FROM Fn_ForecastReport_TEST(NULL)
返回502。这非常令人困惑,所以我使用了该函数的代码:
CREATE FUNCTION dbo.Fn_ForecastReport_TEST(@Date DATE = NULL)
RETURNS @ForecastReportTable TABLE
(
InvcLine_SM NVARCHAR(155),
Cust_No NVARCHAR(15),
Cust_Name NVARCHAR(100),
Genus NVARCHAR(20),
S_City NVARCHAR(100),
[Default Whs] NVARCHAR(30),
U_CustChannel NVARCHAR(20),
[ActualKits-2] NUMERIC(38, 17),
[ActualKits-1] NUMERIC(38, 17),
ActualKits NUMERIC(38, 17),
[FC Kits] INT,
[FC Kits+1] INT,
[FC Kits+2] INT,
[FC Sales] NUMERIC(38, 6),
[FC Sales+1] NUMERIC(38, 6),
[FC Sales+2] NUMERIC(38, 6),
[Avg Price] NUMERIC(38, 6)
)
AS
BEGIN
-- If we provide NULL to the function, it will use today's date
SET @Date = ISNULL(@Date, GETDATE());
DECLARE
@TPlus2EndDate AS DATE,
@TPlus2StartDate AS DATE,
@TPlus1EndDate AS DATE,
@TPlus1StartDate AS DATE,
@TMinus0EndDate AS DATE,
@TMinus0StartDate AS DATE,
@TMinus1EndDate AS DATE,
@TMinus1StartDate AS DATE,
@TMinus2EndDate AS DATE,
@TMinus2StartDate AS DATE;
-- We use T Minus 0 as the basis for all other calculations so it needs to be calculated first
SELECT @TMinus0StartDate = FirstDay,
@TMinus0EndDate = LastDay
FROM Fn_GetFirstAndLastDaysOfMonthFromDate(@Date);
SELECT @TPlus2StartDate = FirstDay,
@TPlus2EndDate = LastDay
FROM Fn_GetFirstAndLastDaysOfMonthFromDate(DATEADD(MONTH, 2, @TMinus0StartDate));
SELECT @TPlus1StartDate = FirstDay,
@TPlus1EndDate = LastDay
FROM Fn_GetFirstAndLastDaysOfMonthFromDate(DATEADD(MONTH, 1, @TMinus0StartDate));
SELECT @TMinus1StartDate = FirstDay,
@TMinus1EndDate = LastDay
FROM Fn_GetFirstAndLastDaysOfMonthFromDate(DATEADD(MONTH, -1, @TMinus0StartDate));
SELECT @TMinus2StartDate = FirstDay,
@TMinus2EndDate = LastDay
FROM Fn_GetFirstAndLastDaysOfMonthFromDate(DATEADD(MONTH, -2, @TMinus0StartDate));
WITH Genera_CTE (Genus) AS (
SELECT '106' UNION ALL
SELECT '108' UNION ALL
SELECT '108YM' UNION ALL
SELECT '112' UNION ALL
SELECT '112XC' UNION ALL
SELECT '118'
),
SpecificPricesForEachBusinessPartnerByProductGenus AS (
SELECT T0.cardcode,
T1.U_Genus_Code,
sum((T1.U_NETcontents + 551) * T0.price) [Price]
FROM OSPP T0
INNER JOIN OITM T1 ON T0.ItemCode = T1.ItemCode
WHERE T0.price < 100
AND T1.U_Netcontents BETWEEN 450 AND 552
AND T1.Onhand <> 0
AND T1.U_Genus_Code IN (SELECT Genus FROM Genera_CTE)
GROUP BY T0.cardcode,
T1.U_Genus_Code
),
BestWarehouseForBusinessPartnerCity_CTE AS (
SELECT CardCode,
City,
U_Default_Whs
FROM CRD1
WHERE AdresType = 'S'
AND U_Default_Whs IS NOT NULL
GROUP BY CardCode,
City,
U_Default_Whs
),
MostRecentForecastsForPeriod AS (
SELECT *
FROM Fn_GetMostRecentForecastsForMonthOfDate(@Date)
UNION ALL
SELECT *
FROM Fn_GetMostRecentForecastsForMonthOfDate(@TPlus1StartDate)
UNION ALL
SELECT *
FROM Fn_GetMostRecentForecastsForMonthOfDate(@TPlus2StartDate)
),
ForecastsReformattedForReport AS (
SELECT T1.SlpName,
T0.U_Cust_ID,
T2.CardName,
T0.U_Genus,
T0.U_Ship_City,
'' [Dfl Whs],
T2.U_CustChannel [U_CustChannel],
0 [ActualKits],
0 [ActualKits-1],
0 [ActualKits-2],
SUM(CASE
WHEN T0.U_FC_Month BETWEEN @TMinus0StartDate AND @TMinus0EndDate
THEN T0.U_Sets
ELSE 0
END) [Forecast],
SUM(CASE
WHEN T0.U_FC_Month BETWEEN @TPlus1StartDate AND @TPlus1EndDate
THEN T0.U_Sets
ELSE 0
END) [Forecast+1],
SUM(CASE
WHEN T0.U_FC_Month BETWEEN @TPlus2StartDate AND @TPlus2EndDate
THEN T0.U_Sets
ELSE 0
END) [Forecast+2]
FROM MostRecentForecastsForPeriod T0
INNER JOIN OSLP T1 ON T0.U_SLP_ID = T1.SlpCode
INNER JOIN OCRD T2 ON T0.U_Cust_ID = T2.CardCode
WHERE T0.U_FC_Month BETWEEN @TMinus0StartDate AND @TPlus2EndDate
GROUP BY T1.SlpName,
T0.U_Cust_ID,
T2.CardName,
T0.U_Genus,
T0.U_Ship_City,
T2.U_CustChannel
),
ActualTransactionsFormattedForReport AS (
SELECT InvcLine_SM,
Cust_No,
Cust_Name,
Genus,
S_City,
CASE
WHEN U_Default_Whs IS NULL THEN 'Mesa Dflt'
ELSE U_Default_Whs
END AS 'Default Whs',
U_CustChannel,
SUM(CASE
WHEN Trx_Date BETWEEN @TMinus0StartDate AND @TMinus0EndDate
THEN Kits
ELSE 0
END) [ActualKits],
SUM(CASE
WHEN Trx_Date BETWEEN @TMinus1StartDate AND @TMinus1EndDate
THEN Kits
ELSE 0
END) [ActualKits-1],
SUM(CASE
WHEN Trx_Date BETWEEN @TMinus2StartDate AND @TMinus2EndDate
THEN Kits
ELSE 0
END) [ActualKits-2],
0 [Forecast],
0 [Forecast+1],
0 [Forecast+2]
FROM SWD_SALES_TRX
WHERE Genus IN (SELECT Genus FROM Genera_CTE)
AND Trx_Date BETWEEN @TMinus2StartDate AND @TMinus0EndDate
GROUP BY InvcLine_SM,
cust_no,
Cust_name,
U_Default_Whs,
Genus,
S_City,
U_CustChannel
),
TransactionsAndForecastsMergedForReport AS (
SELECT *
FROM ActualTransactionsFormattedForReport
UNION ALL
SELECT *
FROM ForecastsReformattedForReport
)
INSERT @ForecastReportTable
SELECT
T0.InvcLine_SM,
T0.Cust_No,
T0.Cust_Name,
T0.Genus,
T0.S_City,
CASE
WHEN MAX(A0.U_Default_Whs) = ''
OR MAX(A0.U_Default_Whs) IS NULL
THEN 'Mesa Dflt'
ELSE MAX(A0.U_Default_Whs)
END [Default Whs],
T0.U_CustChannel,
SUM(T0.[ActualKits-2]) [ActualKits-2],
SUM(T0.[ActualKits-1]) [ActualKits-1],
SUM(T0.[ActualKits]) [ActualKits],
Sum(T0.[Forecast]) [FC Kits],
Sum(T0.[Forecast+1]) [FC Kits+1],
Sum(T0.[Forecast+2]) [FC Kits+2],
SUM(T0.[Forecast]) * ISNULL(T5.Price, t6.total) [FC Sales],
SUM(T0.[Forecast+1]) * ISNULL(T5.Price, t6.total) [FC Sales+1],
SUM(T0.[Forecast+2]) * ISNULL(T5.Price, t6.total) [FC Sales+2],
MAX(T6.Total) [Avg Price]
FROM TransactionsAndForecastsMergedForReport T0
LEFT JOIN SpecificPricesForEachBusinessPartnerByProductGenus T5 ON T0.Cust_No = T5.CardCode
AND T5.U_Genus_Code = T0.Genus
LEFT JOIN (
SELECT T2.U_CustChannel,
T1.U_Genus_Code,
(CASE
WHEN SUM(CASE
WHEN T1.[InvntryUom] <> 'KIT'
THEN T0.Quantity
ELSE T0.Quantity * ISNULL(T1.U_NetContents, 1)
END) = 0
THEN 0
ELSE sum(T0.LineTotal) / SUM(CASE
WHEN T1.[InvntryUom] <> 'KIT'
THEN T0.Quantity
ELSE T0.Quantity * ISNULL(551 + T1.U_NetContents, 1)
END)
END) * (MAX(T1.U_NetContents) + 551) [Total]
FROM (
SELECT T0.CardCode,T1.LineTotal [LineTotal],T1.Quantity [Quantity],T1.ItemCode
FROM OINV T0
INNER JOIN INV1 T1 ON T0.DocEntry = T1.DocEntry
WHERE T0.Canceled = 'N'
AND (T1.LineTotal <> 0 OR TreeType = 'N')
UNION ALL
SELECT T0.CardCode,(T1.LineTotal) * -1 [LineTotal], -T1.Quantity [Quantity],T1.ItemCode
FROM ORIN T0
INNER JOIN RIN1 T1 ON T0.DocEntry = T1.DocEntry
WHERE T0.Canceled = 'N'
AND T0.docType <> 'S'
AND T0.CANCELED = 'N'
AND (T1.LineTotal <> 0 OR TreeType = 'N')
) T0
INNER JOIN OITM T1 ON T0.ItemCode = T1.ItemCode
INNER JOIN OCRD T2 ON T0.CardCode = T2.CardCode
WHERE T1.U_Netcontents BETWEEN 450 AND 552
AND t1.Onhand <> 0
AND (
T1.U_Genus_Code IN (SELECT Genus FROM Genera_CTE)
OR (T1.[InvntryUom] = 'KIT' AND T1.U_Genus_Code = '108')
)
GROUP BY T2.U_CustChannel,
T1.U_Genus_Code
) T6 ON T6.U_CustChannel = T0.U_CustChannel
AND T6.U_Genus_Code = T0.Genus
LEFT JOIN BestWarehouseForBusinessPartnerCity_CTE A0 ON A0.CardCode = T0.Cust_No
AND LOWER(A0.City) = LOWER(T0.S_City)
GROUP BY InvcLine_SM,
cust_no,
Cust_name,
genus,
S_City,
t5.price,
t6.total,
T0.U_CustChannel;
RETURN;
END
GO
我稍微修改了此SQL,以便可以在函数外部运行它,并且我注意到一些非常奇怪的东西,那就是当我在函数外部运行它时,错误消失了:
-- If we provide NULL to the function, it will use today's date
DECLARE @Date DATE = GETDATE();
DECLARE
@TPlus2EndDate AS DATE,
@TPlus2StartDate AS DATE,
@TPlus1EndDate AS DATE,
@TPlus1StartDate AS DATE,
@TMinus0EndDate AS DATE,
@TMinus0StartDate AS DATE,
@TMinus1EndDate AS DATE,
@TMinus1StartDate AS DATE,
@TMinus2EndDate AS DATE,
@TMinus2StartDate AS DATE;
-- We use T Minus 0 as the basis for all other calculations so it needs to be calculated first
SELECT @TMinus0StartDate = FirstDay,
@TMinus0EndDate = LastDay
FROM Fn_GetFirstAndLastDaysOfMonthFromDate(@Date);
SELECT @TPlus2StartDate = FirstDay,
@TPlus2EndDate = LastDay
FROM Fn_GetFirstAndLastDaysOfMonthFromDate(DATEADD(MONTH, 2, @TMinus0StartDate));
SELECT @TPlus1StartDate = FirstDay,
@TPlus1EndDate = LastDay
FROM Fn_GetFirstAndLastDaysOfMonthFromDate(DATEADD(MONTH, 1, @TMinus0StartDate));
SELECT @TMinus1StartDate = FirstDay,
@TMinus1EndDate = LastDay
FROM Fn_GetFirstAndLastDaysOfMonthFromDate(DATEADD(MONTH, -1, @TMinus0StartDate));
SELECT @TMinus2StartDate = FirstDay,
@TMinus2EndDate = LastDay
FROM Fn_GetFirstAndLastDaysOfMonthFromDate(DATEADD(MONTH, -2, @TMinus0StartDate));
WITH Genera_CTE (Genus) AS (
SELECT '106' UNION ALL
SELECT '108' UNION ALL
SELECT '108YM' UNION ALL
SELECT '112' UNION ALL
SELECT '112XC' UNION ALL
SELECT '118'
),
SpecificPricesForEachBusinessPartnerByProductGenus AS (
SELECT T0.cardcode,
T1.U_Genus_Code,
sum((T1.U_NETcontents + 551) * T0.price) [Price]
FROM OSPP T0
INNER JOIN OITM T1 ON T0.ItemCode = T1.ItemCode
WHERE T0.price < 100
AND T1.U_Netcontents BETWEEN 450 AND 552
AND T1.Onhand <> 0
AND T1.U_Genus_Code IN (SELECT Genus FROM Genera_CTE)
GROUP BY T0.cardcode,
T1.U_Genus_Code
),
BestWarehouseForBusinessPartnerCity_CTE AS (
SELECT CardCode,
City,
U_Default_Whs
FROM CRD1
WHERE AdresType = 'S'
AND U_Default_Whs IS NOT NULL
GROUP BY CardCode,
City,
U_Default_Whs
),
MostRecentForecastsForPeriod AS (
SELECT *
FROM Fn_GetMostRecentForecastsForMonthOfDate(@Date)
UNION ALL
SELECT *
FROM Fn_GetMostRecentForecastsForMonthOfDate(@TPlus1StartDate)
UNION ALL
SELECT *
FROM Fn_GetMostRecentForecastsForMonthOfDate(@TPlus2StartDate)
),
ForecastsReformattedForReport AS (
SELECT T1.SlpName,
T0.U_Cust_ID,
T2.CardName,
T0.U_Genus,
T0.U_Ship_City,
'' [Dfl Whs],
T2.U_CustChannel [U_CustChannel],
0 [ActualKits],
0 [ActualKits-1],
0 [ActualKits-2],
SUM(CASE
WHEN T0.U_FC_Month BETWEEN @TMinus0StartDate AND @TMinus0EndDate
THEN T0.U_Sets
ELSE 0
END) [Forecast],
SUM(CASE
WHEN T0.U_FC_Month BETWEEN @TPlus1StartDate AND @TPlus1EndDate
THEN T0.U_Sets
ELSE 0
END) [Forecast+1],
SUM(CASE
WHEN T0.U_FC_Month BETWEEN @TPlus2StartDate AND @TPlus2EndDate
THEN T0.U_Sets
ELSE 0
END) [Forecast+2]
FROM MostRecentForecastsForPeriod T0
INNER JOIN OSLP T1 ON T0.U_SLP_ID = T1.SlpCode
INNER JOIN OCRD T2 ON T0.U_Cust_ID = T2.CardCode
WHERE T0.U_FC_Month BETWEEN @TMinus0StartDate AND @TPlus2EndDate
GROUP BY T1.SlpName,
T0.U_Cust_ID,
T2.CardName,
T0.U_Genus,
T0.U_Ship_City,
T2.U_CustChannel
),
ActualTransactionsFormattedForReport AS (
SELECT InvcLine_SM,
Cust_No,
Cust_Name,
Genus,
S_City,
CASE
WHEN U_Default_Whs IS NULL THEN 'Mesa Dflt'
ELSE U_Default_Whs
END AS 'Default Whs',
U_CustChannel,
SUM(CASE
WHEN Trx_Date BETWEEN @TMinus0StartDate AND @TMinus0EndDate
THEN Kits
ELSE 0
END) [ActualKits],
SUM(CASE
WHEN Trx_Date BETWEEN @TMinus1StartDate AND @TMinus1EndDate
THEN Kits
ELSE 0
END) [ActualKits-1],
SUM(CASE
WHEN Trx_Date BETWEEN @TMinus2StartDate AND @TMinus2EndDate
THEN Kits
ELSE 0
END) [ActualKits-2],
0 [Forecast],
0 [Forecast+1],
0 [Forecast+2]
FROM SWD_SALES_TRX
WHERE Genus IN (SELECT Genus FROM Genera_CTE)
AND Trx_Date BETWEEN @TMinus2StartDate AND @TMinus0EndDate
GROUP BY InvcLine_SM,
cust_no,
Cust_name,
U_Default_Whs,
Genus,
S_City,
U_CustChannel
),
TransactionsAndForecastsMergedForReport AS (
SELECT *
FROM ActualTransactionsFormattedForReport
UNION ALL
SELECT *
FROM ForecastsReformattedForReport
),
FinalOutput AS (
SELECT T0.InvcLine_SM,
T0.Cust_No,
T0.Cust_Name,
T0.Genus,
T0.S_City,
CASE
WHEN MAX(A0.U_Default_Whs) = ''
OR MAX(A0.U_Default_Whs) IS NULL
THEN 'Mesa Dflt'
ELSE MAX(A0.U_Default_Whs)
END [Default Whs],
T0.U_CustChannel,
SUM(T0.[ActualKits-2]) [ActualKits-2],
SUM(T0.[ActualKits-1]) [ActualKits-1],
SUM(T0.[ActualKits]) [ActualKits],
Sum(T0.[Forecast]) [FC Kits],
Sum(T0.[Forecast+1]) [FC Kits+1],
Sum(T0.[Forecast+2]) [FC Kits+2],
SUM(T0.[Forecast]) * ISNULL(T5.Price, t6.total) [FC Sales],
SUM(T0.[Forecast+1]) * ISNULL(T5.Price, t6.total) [FC Sales+1],
SUM(T0.[Forecast+2]) * ISNULL(T5.Price, t6.total) [FC Sales+2],
MAX(T6.Total) [Avg Price]
FROM TransactionsAndForecastsMergedForReport T0
LEFT JOIN SpecificPricesForEachBusinessPartnerByProductGenus T5 ON T0.Cust_No = T5.CardCode
AND T5.U_Genus_Code = T0.Genus
LEFT JOIN (
SELECT T2.U_CustChannel,
T1.U_Genus_Code,
(CASE
WHEN SUM(CASE
WHEN T1.[InvntryUom] <> 'KIT'
THEN T0.Quantity
ELSE T0.Quantity * ISNULL(T1.U_NetContents, 1)
END) = 0
THEN 0
ELSE sum(T0.LineTotal) / SUM(CASE
WHEN T1.[InvntryUom] <> 'KIT'
THEN T0.Quantity
ELSE T0.Quantity * ISNULL(551 + T1.U_NetContents, 1)
END)
END) * (MAX(T1.U_NetContents) + 551) [Total]
FROM (
SELECT T0.CardCode,T1.LineTotal [LineTotal],T1.Quantity [Quantity],T1.ItemCode
FROM OINV T0
INNER JOIN INV1 T1 ON T0.DocEntry = T1.DocEntry
WHERE T0.Canceled = 'N'
AND (T1.LineTotal <> 0 OR TreeType = 'N')
UNION ALL
SELECT T0.CardCode,(T1.LineTotal) * -1 [LineTotal], -T1.Quantity [Quantity],T1.ItemCode
FROM ORIN T0
INNER JOIN RIN1 T1 ON T0.DocEntry = T1.DocEntry
WHERE T0.Canceled = 'N'
AND T0.docType <> 'S'
AND T0.CANCELED = 'N'
AND (T1.LineTotal <> 0 OR TreeType = 'N')
) T0
INNER JOIN OITM T1 ON T0.ItemCode = T1.ItemCode
INNER JOIN OCRD T2 ON T0.CardCode = T2.CardCode
WHERE T1.U_Netcontents BETWEEN 450 AND 552
AND t1.Onhand <> 0
AND (
T1.U_Genus_Code IN (SELECT Genus FROM Genera_CTE)
OR (T1.[InvntryUom] = 'KIT' AND T1.U_Genus_Code = '108')
)
GROUP BY T2.U_CustChannel,
T1.U_Genus_Code
) T6 ON T6.U_CustChannel = T0.U_CustChannel
AND T6.U_Genus_Code = T0.Genus
LEFT JOIN BestWarehouseForBusinessPartnerCity_CTE A0 ON A0.CardCode = T0.Cust_No
AND LOWER(A0.City) = LOWER(T0.S_City)
GROUP BY InvcLine_SM,
cust_no,
Cust_name,
genus,
S_City,
t5.price,
t6.total,
T0.U_CustChannel
)
SELECT count(*)
FROM FinalOutput;
本质上,唯一的变化是将@Date切换为DECLARE而不是SET,并删除了函数输出的INSERT。是否存在一些使函数返回的值与实际行数不同的函数的怪癖?
答案 0 :(得分:0)
这是JetBrain的DataGrip产品的问题。当我在SSMS中运行相同的代码时,它为COUNT返回了正确的金额。
答案 1 :(得分:0)
SQL Server有时在sys.sysindexes表/视图中提供的信息不正确...试图更新索引和统计信息,并查看其是否仍然不匹配。
如果清除,则count(*)正在将其行计数从索引而不是表中移出,而select返回实际行。
nvm,jetbrain做到了!多么糟糕!