0

我有一个跟踪共同基金投资的网站。为此,我有下表结构(结构已被修改以删除不需要的列,以便专注于我的问题)

表#1:scheme_Mst

|Scheme_ID | fundHouse_Id | OpeningBalance | OpeningUnits
----------------------------------------------------------
|1         |  1           | 100            |  10 

表#2 投资

|Scheme_ID | InvestedAmt   | InvestedUnits | statusFlag
----------------------------------------------------------
|1         | 50            |  5            | A

表#3兑换

|Scheme_ID | redemedAmt    | redemedUnits  | statusFlag
----------------------------------------------------------
|1         | 50            |  5            | A

表#4 SwitchDetails

|From_Scheme_ID |To_Scheme_ID |switchInAmt |switchInUnits |switchOutAmt |switchOutUnits | StaFlag
------------------------------------------------------------------------------------------
|1              | 2           | 20         | 2            | 10          | 1             | A

表 #5 奖金详情

|Scheme_ID | BonusAmt   | BonusUnits | statusFlag
----------------------------------------------------------
|1         | 50         |  5         | A

表#6 Divident_Details

|Scheme_ID | DividentAmt | DividentUnits | statusFlag
----------------------------------------------------------
|1         | 50          |  5            | A

现在要详细了解我在下面查询的方案中可用单位的详细信息......(这是非常非常昂贵的)

SELECT *,
       CASE
           WHEN OutstandingUnits <> 0 THEN CONVERT(decimal(18,2),Outstanding/OutstandingUnits)
           ELSE 0
       END AS WAC
FROM
  (SELECT *,
          ISNULL(OpeningBalance,0) + ISNULL(DividendAmount,0) + ISNULL(bonusAmount,0) + ISNULL(invstAmount,0) + ISNULL(SwitchedInAmount,0) - ISNULL(redeemedAmount,0) - ISNULL(SwitchedOutAmount,0) AS Outstanding,
          ISNULL(openingUnits,0) + ISNULL(DividendUnits,0) + ISNULL(bonusUnits,0) + ISNULL(invstUnits,0) + SNULL(SwitchedInUnits,0) - ISNULL(redeemedUnits,0) - ISNULL(SwitchedOutUnits,0) AS OutstandingUnits
   FROM
     (SELECT C.scheme_ID,D.schemeName, D.Openingbalance AS OpeningBalance, D.OpeningUnits AS openingUnits, ISNULL(SUM(C.invstAmount),0) AS invstAmount, ISNULL(SUM(C.invstUnits),0) AS invstUnits,
        (SELECT ISNULL(SUM(redemedAmt),0)
         FROM redemption
         WHERE StatusFlag='A'
           AND scheme_ID = C.scheme_ID) AS redeemedAmount,
        (SELECT ISNULL(SUM(redeemedUnits),0)
         FROM redemption
         WHERE StatusFlag='A'
           AND scheme_ID = C.scheme_ID) AS redeemedUnits,
        (SELECT ISNULL(sum(switchOutAmt),0)
         FROM SwitchDetails
         WHERE BB.Status = 'A'
           AND BB.From_Scheme_Id = C.scheme_ID) AS SwitchedOutAmount,
        (SELECT ISNULL(sum(switchOutUnits),0)
         FROM SwitchDetails
         WHERE BB.Status = 'A'
           AND BB.From_Scheme_Id = C.scheme_ID) AS SwitchedOutUnits,
        (SELECT ISNULL(sum(switchOutAmt),0)
         FROM SwitchDetails
         WHERE BB.Status = 'A'
           AND BB.From_Scheme_Id = C.scheme_ID) AS SwitchedInAmount,
        (SELECT ISNULL(sum(SwitchedInUnits),0)
         FROM SwitchDetails
         WHERE BB.Status = 'A'
           AND BB.From_Scheme_Id = C.scheme_ID) AS SwitchedInUnits, .. same way
      FOR bonus
      AND divident ..
      FROM Investment c) tab)tab2

此查询应该产生以下输出..(示例输出)

Scheme_ID| Scheme_Name | OpeningBalance | OpeningUnits | InvstAmount | invstUnits | redemedAmount | redemedUnits | SwitchedOutAmt | SwitchOutUnit | bonusAmt | bonusUnit | DividentAmount | DividentUnit | Outstanding | OutstandingUnit | WAC
-------------------------------------------------------------------------------------------

这就是我计算细节的方式。请建议我更好的方法。

我正在使用 sql server 2008

4

2 回答 2

0

在这种情况下,具有相同条件的子查询可能是性能最差的敌人。

试试这个你的内部查询:

SELECT 
    c.scheme_ID,
    d.schemeName,
    d.Openingbalance AS OpeningBalance,
    d.OpeningUnits AS openingUnits,
    ISNULL(SUM(c.invstAmount), 0) AS invstAmount,
    ISNULL(SUM(c.invstUnits), 0) AS invstUnits,

    ISNULL(SUM(r.redemedAmt), 0) AS redeemedAmount,
    ISNULL(SUM(r.redeemedUnits), 0) AS redeemedUnits, 
    ISNULL(SUM(r.switchOutAmt), 0) AS SwitchedOutAmount,
    ISNULL(SUM(r.switchOutUnits), 0) AS SwitchedOutUnits,
    ISNULL(SUM(r.switchOutAmt), 0) AS SwitchedInAmount,
    ISNULL(SUM(r.SwitchedInUnits), 0) AS SwitchedInUnits
FROM Investment AS c
INNER JOIN redemption AS r 
    ON r.StatusFlag='A' AND r.scheme_ID = C.scheme_ID
--INNER JOIN someTable AS d...
于 2013-11-15T07:34:29.410 回答
0

你可以做这样的事情(我没有插入GROUP BY子句或总结Openingbalance, OpeningUnits你更好地了解你的查询逻辑,我只是​​为了性能而编辑):

SELECT *,
       CASE
           WHEN OutstandingUnits <> 0 THEN CONVERT(decimal(18,2),Outstanding/OutstandingUnits)
           ELSE 0
       END AS WAC
FROM
     (SELECT C.scheme_ID,
             D.schemeName, 
             D.Openingbalance AS OpeningBalance, 
             D.OpeningUnits AS openingUnits, 
             ISNULL(SUM(C.invstAmount),0) AS invstAmount, 
             ISNULL(SUM(C.invstUnits),0) AS invstUnits,
         ISNULL(SUM(r.redemedAmt),0) redeemedAmount,
         ISNULL(SUM(r.redeemedUnits),0) redeemedUnits,
         ISNULL(sum(sd.switchOutAmt),0) SwitchedOutAmount,
         ISNULL(sum(sd.switchOutUnits),0) SwitchedOutUnits,
         ISNULL(sum(sd.switchOutAmt),0) SwitchedInAmount,
         ISNULL(sum(sd.SwitchedInUnits),0) SwitchedInUnits,
          --The sum columns from above query
          ISNULL(OpeningBalance,0) + ISNULL(DividendAmount,0) + ISNULL(bonusAmount,0) + ISNULL(invstAmount,0) + 
          ISNULL(SwitchedInAmount,0) - ISNULL(redeemedAmount,0) - ISNULL(SwitchedOutAmount,0) AS Outstanding,
          ISNULL(openingUnits,0) + ISNULL(DividendUnits,0) + ISNULL(bonusUnits,0) + ISNULL(invstUnits,0) + 
          ISNULL(SwitchedInUnits,0) - ISNULL(redeemedUnits,0) - ISNULL(SwitchedOutUnits,0) AS OutstandingUnits,
          ----
      .. same way
      FOR bonus
      AND divident ..
      FROM Investment c
      LEFT JOIN redemption r
       ON r.StatusFlag='A'
       AND r.scheme_ID = C.scheme_ID
      LEFT JOIN SwitchDetails sd
       ON sd.Status = 'A'
       AND sd.From_Scheme_Id = C.scheme_ID
       ) tab
于 2013-11-15T07:36:38.653 回答