2014-08-28 46 views
1

我正在創建用於搜索的存儲過程。 DateOrdereddatetime類型表中的列名。如何在日期時間存儲過程中使用BETWEEN

問題是我想對此列執行搜索。用戶可以搜索開始日期和結束日期。另外,用戶可以爲任何參數發送null,例如開始日期或結束日期。

當用戶不會發送開始日期或結束日期時,我將搜索另一個選項。我的問題是,我如何處理下面是我試過的查詢,但沒有成功

SELECT 
    @C_Order_ID = C_Order_ID 
FROM 
    C_Order COrder 
WHERE 
    (@AD_Org_ID IS NULL OR 
    COrder.AD_Org_ID IN (SELECT ID FROM fnSplitter(@AD_Org_ID))) 
    AND (@AD_Client_ID IS NULL OR 
     @AD_Client_ID IN (SELECT ID FROM fnSplitter(@AD_Client_ID))) 
    AND (@IsActive IS NULL OR COrder.IsActive = @IsActive) 
    AND (@startDate IS NULL OR 
     COrder.DateOrdered = @startDate BETWEEN @EndDate IS NULL 
      OR COrder.DateOrdered = @EndDate) 

感謝您的回覆。

回答

1

你可以嘗試這樣的:

COrder.DateOrdered BETWEEN @startDate AND @EndDate 

所以,你的查詢將會像

SELECT @C_Order_ID= C_Order_ID FROM C_Order COrder 
WHERE 
    (@AD_Org_ID IS NULL OR COrder.AD_Org_ID IN (Select ID From fnSplitter(@AD_Org_ID))) 
AND (@AD_Client_ID IS NULL OR @AD_Client_ID IN (Select ID From fnSplitter(@AD_Client_ID))) 
AND (@IsActive IS NULL OR COrder.IsActive = @IsActive) 
AND (@startDate IS NULL OR COrder.DateOrdered BETWEEN isnull(@startDate,'') AND isnull(@EndDate,'')) 

或更好

SELECT @C_Order_ID= C_Order_ID FROM C_Order COrder 
    WHERE 
     (@AD_Org_ID IS NULL OR COrder.AD_Org_ID IN (Select ID From fnSplitter(@AD_Org_ID))) 
    AND (@AD_Client_ID IS NULL OR @AD_Client_ID IN (Select ID From fnSplitter(@AD_Client_ID))) 
    AND (@IsActive IS NULL OR COrder.IsActive = @IsActive) 
    AND (CAST(@startDate AS DATE) IS NULL OR (CAST(@startDate AS DATE) IS NULL OR CAST(COrder.DateOrdered AS DATE) >=CAST(@startDate AS DATE)) 
    AND (CAST(@endDate AS DATE) IS NULL OR CAST(COrder.DateOrdered AS DATE) <=CAST(@endDate AS DATE)) 
+0

@ R.T。如果用戶將發送空值然後 – 2014-08-28 07:12:38

+0

@ A.Goutam: - 更新我的答案來處理! – 2014-08-28 07:14:53

+0

但我的領域是類型的日期時間,我只想不爲日期時間 – 2014-08-28 07:16:16

0
SELECT @C_Order_ID= C_Order_ID FROM C_Order COrder 
WHERE 
(@AD_Org_ID IS NULL OR COrder.AD_Org_ID IN (Select ID From fnSplitter(@AD_Org_ID))) 
AND (@AD_Client_ID IS NULL OR @AD_Client_ID IN (Select ID From fnSplitter(@AD_Client_ID))) 
AND (@IsActive IS NULL OR COrder.IsActive = @IsActive) 
AND (@startDate IS NULL OR COrder.DateOrdered BETWEEN @startDate AND @EndDate 
OR COrder.DateOrdered = @EndDate) 
+0

如果用戶將發送空值,那麼這將如何處理 – 2014-08-28 07:13:42

0

Aaron Bertrand已經撰寫了有關使用的好文章與日期範圍之間 - What do BETWEEN and the devil have in common?,這值得一讀。此外,它看起來像你傳遞一個字符串中的逗號分隔的列表,然後用功能fnsplitter拆分它,你可能要考慮使用table-valued paramters

但是,要真正回答你的問題,你可以使用不使用上述想法之間並將您的查詢更改爲:

AND (@startDate IS NULL OR COrder.DateOrdered >= @startDate) 
AND (@EndDate IS NULL OR COrder.DateOrdered <= @EndDate) 

因此,您有4個排列組合。

  1. 兩個@StartDate和@EndDate爲空 - 返回所有日期
  2. @StartDate不是null @EndDate爲空 - @StartDate後返回的所有日期
  3. @StartDate爲null,並且@EndDate不空 - @EndDate
  4. 之前返回所有日期
  5. 兩個@StartDate和@EndDate不是空 - 返回@StartDate和@EndDate

根據對另一個答案您的意見之間的所有日期,這聽起來像你可能通過作爲@EndDate參數的日期,例如2014-08-28,但仍希望包括該日期的所有記錄,即使它們有時間相關,例如, 2014-08-28 12:00,這也正是爲什麼之間不使用的日期範圍,而不是你需要使用不到運營商1天添加到您的結束日期:

AND (@startDate IS NULL OR COrder.DateOrdered >= @startDate) 
AND (@EndDate IS NULL OR COrder.DateOrdered < DATEADD(DAY, 1, @EndDate)) 
相關問題