0

在这里,我们在一个存储过程中加入多个 select 语句。在每个嵌套查询中,我们对 year 参数和其他一些参数进行过滤。我确信存在会损害性能的冗余,但不确定如何改进。任何想法?谢谢!

SELECT Months.MonthName, 
GPSDailyAccruals.MonthNumber,
GPSDailyAccruals.YearNumber,
ISNULL(GPSDailyAccruals.Amount,0) AS GPSDailyAccrualAmount,
ISNULL(GPSMonthlyAccruals.Amount,0) AS GPSMonthlyAccrualAmount,
ISNULL(GPSMonthlyAccrualsReceivable.Amount,0) AS GPSMonthlyAccrualReceivableAmount,
ISNULL(GMIDailyAccruals.Amount,0) AS GMIDailyAccrualAmount,
ISNULL(GLPayable.AMOUNT,0) AS GLPayable,
+ISNULL(Paid.AMOUNT,0) AS Paid,
ISNULL(GMIDailyAccruals.Amount,0)-ISNULL(Paid.AMOUNT,0) AS GMIvsPAID,
ISNULL(AdjustmentsLateTradeAmount.Amount,0) AS AdjustmentsLateTradeAmount,
ISNULL(GMIDailyAccruals.Amount,0) + ISNULL(AdjustmentsLateTradeAmount.Amount,0) - ISNULL(GLPayable.AMOUNT,0) AS GLOOB,
CASE WHEN ISNULL(MatchedTrades.Amount,0) <> 0 AND ISNULL(TotalTrades.Amount,0) <> 0  THEN (CONVERT(numeric,MatchedTrades.Amount) / CONVERT(numeric,TotalTrades.Amount)) * 100 ELSE 0 END AS MatchingPercentage

FROM
(
    SELECT Months.MonthNumber, 
    Months.MonthName
    FROM Months
) Months

LEFT JOIN (
SELECT MONTH(TradeDate) AS MonthNumber,
YEAR(TradeDate) AS YearNumber,
SUM(CASE WHEN RecordType = 'C' THEN Fee ELSE Fee*-1 END) AS Amount
FROM vFutureCMEGPSPay
WHERE YEAR(TradeDate) = @year
AND StatusID <> 4
AND IsCancel = 'N'
GROUP BY MONTH(TradeDate), YEAR(TradeDate)
) GPSDailyAccruals
ON Months.MonthNumber = GPSDailyAccruals.MonthNumber

LEFT JOIN (
SELECT MonthNumber,
YearNumber,
SUM(CASE WHEN RecordType = 'C' THEN Fee ELSE Fee*-1 END) AS Amount
FROM TradeCMEGPSMonthly
WHERE YearNumber = @year
AND Expired_CarryoverIndicator NOT IN ('E','C')
GROUP BY MonthNumber, YearNumber
) GPSMonthlyAccruals
ON Months.MonthNumber = GPSMonthlyAccruals.MonthNumber

LEFT JOIN (
SELECT MonthNumber,
YearNumber,
SUM(Fee) AS Amount
FROM TradeCMEGPSMonthly
WHERE YearNumber = @year
AND RecordType = 'E'
AND Expired_CarryoverIndicator NOT IN ('E','C')
GROUP BY MonthNumber, YearNumber
) GPSMonthlyAccrualsReceivable
ON Months.MonthNumber = GPSMonthlyAccrualsReceivable.MonthNumber

LEFT JOIN (
SELECT MONTH(TradeDate) AS MonthNumber,
YEAR(TradeDate) AS YearNumber,
SUM(CASE WHEN AssetClassCode = 'Z' THEN PCOMM * -1 ELSE POTHER END)*-1 AS Amount
FROM vFutureCMEGPSGMIPay
WHERE YEAR(TradeDate) = @year
AND StatusID <> 4
GROUP BY MONTH(TradeDate), YEAR(TradeDate)
) GMIDailyAccruals
ON Months.MonthNumber = GMIDailyAccruals.MonthNumber

LEFT JOIN (
SELECT 
MonthNumber,
YearNumber,
SUM(AMOUNT)*-1 AS Amount
FROM (
    SELECT DISTINCT *
    FROM GMIGeneralLedger
    WHERE YearNumber = @year
    AND GL_ACCOUNT_NBR = '4402795'
    AND ATTRIBUTE1 NOT LIKE '%GPS SETTLEMENT%'
    ) GMIGeneralLedger
GROUP BY MonthNumber, YearNumber
) GLPayable
ON Months.MonthNumber = GLPayable.MonthNumber

LEFT JOIN (
SELECT 
MonthNumber,
YearNumber,
SUM(AMOUNT) AS Amount
FROM (
    SELECT DISTINCT *
    FROM GMIGeneralLedger
    WHERE YearNumber = @year
    AND GL_ACCOUNT_NBR = '4402795'
    AND ATTRIBUTE1 LIKE '%GPS SETTLEMENT%'
    ) GMIGeneralLedger
GROUP BY MonthNumber, YearNumber
) Paid
ON Months.MonthNumber = Paid.MonthNumber    

LEFT JOIN (
SELECT AdjustmentMonth,
AdjustmentYear,
SUM(Amount)*-1 AS Amount
FROM AdjustmentFutureWFSPayable
WHERE ModuleID = 9
AND AdjustmentYear = @year
GROUP BY AdjustmentMonth, AdjustmentYear
) AdjustmentsLateTradeAmount
ON Months.MonthNumber = AdjustmentsLateTradeAmount.AdjustmentMonth

LEFT JOIN (
SELECT MONTH(TradeDate) AS MonthNumber,
YEAR(TradeDate) AS YearNumber,
COUNT(TradeStatusID) AS Amount
FROM TradeCMEGPS
INNER JOIN TradeStatus ON TradeCMEGPS.TradeID = TradeStatus.TradeID AND ModuleID = 9 AND SourceSystemID = 7
WHERE YEAR(TradeDate) = @year
AND TradeStatus.StatusID <> 4
GROUP BY MONTH(TradeDate), YEAR(TradeDate)
) TotalTrades
ON Months.MonthNumber = TotalTrades.MonthNumber

LEFT JOIN (
SELECT MONTH(TradeDate) AS MonthNumber,
YEAR(TradeDate) AS YearNumber,
COUNT(TradeStatusID) AS Amount
FROM TradeCMEGPS
INNER JOIN TradeStatus ON TradeCMEGPS.TradeID = TradeStatus.TradeID AND ModuleID = 9 AND SourceSystemID = 7
WHERE YEAR(TradeDate) = @year
AND MatchingGroupID IS NOT NULL
GROUP BY MONTH(TradeDate), YEAR(TradeDate)
) MatchedTrades
ON Months.MonthNumber = MatchedTrades.MonthNumber
4

1 回答 1

0

这里有很多错误的地方,具有相同基表和逻辑的多个连接,只是为了获得另一个计算,在同一个连接中进行。当没有必要时,您还继续按年份分组。这是一个版本(可能在某处有错字),它遵循我刚刚给你的建议:

SELECT  Months.MonthName, 
        GPSDailyAccruals.MonthNumber,
        @year YearNumber,
        ISNULL(GPSDailyAccruals.Amount,0) AS GPSDailyAccrualAmount,
        ISNULL(GPSMonthlyAccruals.Amount,0) AS GPSMonthlyAccrualAmount,
        ISNULL(GPSMonthlyAccruals.AmountReceivable,0) AS GPSMonthlyAccrualReceivableAmount,
        ISNULL(GMIDailyAccruals.Amount,0) AS GMIDailyAccrualAmount,
        ISNULL(GLPayable.AMOUNT*-1,0) AS GLPayable,
        ISNULL(GLPayable.AMOUNT,0) AS Paid,
        ISNULL(GMIDailyAccruals.Amount,0)-ISNULL(GLPayable.AMOUNT,0) AS GMIvsPAID,
        ISNULL(AdjustmentsLateTradeAmount.Amount,0) AS AdjustmentsLateTradeAmount,
        ISNULL(GMIDailyAccruals.Amount,0) + ISNULL(AdjustmentsLateTradeAmount.Amount,0) - ISNULL(GLPayable.AMOUNT*-1,0) AS GLOOB,
        CASE WHEN ISNULL(TotalTrades.Amount2,0) <> 0 AND ISNULL(TotalTrades.Amount1,0) <> 0  THEN (CONVERT(numeric,TotalTrades.Amount2) / CONVERT(numeric,TotalTrades.Amount1)) * 100 ELSE 0 END AS MatchingPercentage
FROM
(
    SELECT Months.MonthNumber, 
    Months.MonthName
    FROM Months
) Months
LEFT JOIN ( SELECT  MONTH(TradeDate) AS MonthNumber,
                    SUM(CASE WHEN RecordType = 'C' THEN Fee ELSE Fee*-1 END) AS Amount
            FROM vFutureCMEGPSPay
            WHERE YEAR(TradeDate) = @year
            AND StatusID <> 4
            AND IsCancel = 'N'
            GROUP BY MONTH(TradeDate)) GPSDailyAccruals
    ON Months.MonthNumber = GPSDailyAccruals.MonthNumber
LEFT JOIN ( SELECT  MonthNumber,
                    SUM(CASE WHEN RecordType = 'C' THEN Fee ELSE Fee*-1 END) AS Amount,
                    SUM(CASE WHEN RecordType = 'E' THEN Fee END) AmountReceivable
            FROM TradeCMEGPSMonthly
            WHERE YearNumber = @year
            AND Expired_CarryoverIndicator NOT IN ('E','C')
            GROUP BY MonthNumber) GPSMonthlyAccruals
    ON Months.MonthNumber = GPSMonthlyAccruals.MonthNumber
LEFT JOIN ( SELECT  MONTH(TradeDate) AS MonthNumber,
                    SUM(CASE WHEN AssetClassCode = 'Z' THEN PCOMM * -1 ELSE POTHER END)*-1 AS Amount
            FROM vFutureCMEGPSGMIPay
            WHERE YEAR(TradeDate) = @year
            AND StatusID <> 4
            GROUP BY MONTH(TradeDate)) GMIDailyAccruals
    ON Months.MonthNumber = GMIDailyAccruals.MonthNumber
LEFT JOIN ( SELECT  MonthNumber,
                    SUM(AMOUNT) AS Amount
            FROM (  SELECT DISTINCT *
                    FROM GMIGeneralLedger
                    WHERE YearNumber = @year
                    AND GL_ACCOUNT_NBR = '4402795'
                    AND ATTRIBUTE1 NOT LIKE '%GPS SETTLEMENT%'
                  ) GMIGeneralLedger
            GROUP BY MonthNumber) GLPayable
    ON Months.MonthNumber = GLPayable.MonthNumber   
LEFT JOIN ( SELECT  AdjustmentMonth,
                    SUM(Amount)*-1 AS Amount
            FROM AdjustmentFutureWFSPayable
            WHERE ModuleID = 9
            AND AdjustmentYear = @year
            GROUP BY AdjustmentMonth) AdjustmentsLateTradeAmount
    ON Months.MonthNumber = AdjustmentsLateTradeAmount.AdjustmentMonth
LEFT JOIN ( SELECT  MONTH(TradeDate) AS MonthNumber,
                    COUNT(CASE WHEN TradeStatus.StatusID <> 4 THEN TradeStatusID END) AS Amount1,
                    COUNT(CASE WHEN MatchingGroupID IS NOT NULL THEN TradeStatusID END) AS Amount2
            FROM TradeCMEGPS
            INNER JOIN TradeStatus 
                ON TradeCMEGPS.TradeID = TradeStatus.TradeID 
                AND ModuleID = 9 AND SourceSystemID = 7
            WHERE YEAR(TradeDate) = @year
            GROUP BY MONTH(TradeDate)) TotalTrades
    ON Months.MonthNumber = TotalTrades.MonthNumber
于 2013-09-17T15:02:29.863 回答