2011-11-23 153 views
0

我有一個查詢涉及SQL Server中的2個表'Coupons'和'CouponUsedLog',下面的查詢將從這2個表中獲得一些信息供統計學研究使用。不知爲什麼,我覺得儘管我的查詢能夠正常工作,並將結果返回給我,但我覺得我可以用更高效的方式編寫,如果有更好的方法來重寫,有人可以請教一下嗎?我是否使用了太多不必要的變量和連接?謝謝。SQL查詢+更高效的替代

DECLARE @CouponISSUED  int=null 
DECLARE @CouponUSED   int=null 
DECLARE @CouponAVAILABLE  int=null 
DECLARE @CouponEXPIRED  int=null 
DECLARE @CouponLastUsed  Date=null 


--Total CouponIssued 
SET @CouponISSUED = 
(
    select count(*) 

    from Coupon C Left Join 
      couponusedlog CU on C.autoid = CU.Coupon_AutoID 

    where C.VoidedBy is null and 
      C.VoidedOn is null and 
      DeletedBy is null and 
      DeletedOn is null and 
      Card_AutoID in (Select AutoID 
          from Card 
          where MemberID = 'Mem001') 
) 

--Total CouponUsed 
SET @CouponUSED = 
(
    select count(*) 
    from couponusedlog CU Left Join 
      Coupon C on CU.Coupon_AutoID = V.autoid 

    where CU.VoidedBy is null and 
      CU.VoidedOn is null and 
      C.Card_AutoID in (select AutoID 
          from Card 
          where MemberID = 'Mem001') 
) 


SET @CouponAVAILABLE = @CouponISSUED - @CouponUSED 


--Expired Coupons 
SET @CouponEXPIRED = 
(
    select Count(*) 

    from Coupon C Left Join 
      couponusedlog CU on C.autoid = CU.Coupon_AutoID 

    where C.VoidedBy is null and 
      C.VoidedOn is null and 
      deletedBy is null and 
      deletedOn is null and 
      Card_AutoID in (select AutoID 
          from Card 
          where MemberID = 'Mem002') and 
      CONVERT (date, getdate()) > C.expirydate 
) 

--Last Used On 
SET @CouponLastUsed = 
(
    select CONVERT(varchar(10), 
      Max(VU.AddedOn), 103) AS [DD/MM/YYYY] 

    from couponusedlog CU Left Join 
      coupon C on CU.Coupon_AutoID = C.autoid 

    where CU.voidedBy is null and 
      CU.voidedOn is null and 
      C.Card_AutoID in (select AutoID 
          from Card 
          where MemberID = 'Mem002') 
) 



Select @CouponISSUED As Coupon_Issued, 
     @CouponUSED  As Coupon_Used, 
     @CouponAVAILABLE As Coupon_Available, 
     @CouponEXPIRED As Coupon_Expired, 
     @CouponLastUsed As Last_Coupon_UsedOn 
+0

是的,這是針對SQL Server的。 – k80sg

回答

1

一般來說它能夠更好地做事情在一個單一的查詢,如果你,你只是在找東西計數特別是對幾乎相同的數據在四個不同的查詢設置即可。

該查詢通過將您的WHERE子句轉換爲CASE語句的SUMS,將您需要的內容組合到一個查詢中。日期的最大值只是一個正常的事情,你可以做一個計數或總和。

SELECT COUNT(*) couponissued, 
     SUM(CASE 
      WHEN deletedby IS NULL 
        AND deletedon IS NULL THEN 1 
      ELSE 0 
      END) AS couponused, 
     SUM(CASE 
      WHEN deletedby IS NULL 
        AND deletedon IS NULL 
        AND Getdate() > c.expirydate THEN 1 
      ELSE 0 
      END) AS couponex, 
MAX(vu.addedon) CouponEXPIRED 
FROM [couponusedlog] cu 
     LEFT JOIN [Coupon] c 
     ON (cu.coupon_autoid = v.autoid) 
WHERE cu.voidedby IS NULL 
     AND cu.voidedon IS NULL 
     AND (c.card_autoid IN (SELECT [AutoID] 
           FROM [Card] 
           WHERE memberid = 'Mem001')) 

可以再轉化公用表表達式做你的減法和格式化

0

你問這個問題了積極的願望是爲effecient越好,或因實績問題你想糾正?您可以使代碼難於管理,從而提高效率。如果現在表現還好,我會強烈建議你離開它,因爲下一個來的人能夠理解它。如果你製作了一個巨大而有效的sql語句,那麼當你或者其他人想要更新一些關於它的信息時,它將會花費你3倍的時間,因爲你試圖重新弄清楚你在寫信時寫的是什麼它。

+0

易理解取決於你的背景我認爲,例如,我發現康拉德的查詢版本比原來更容易遵循。 –