2017-05-14 86 views
0

有沒有更好的方法(從插入到函數參數的輸入)顯示某個月的數據?函數參數檢查SQL Server中某個月的數據的更好方法

這是我使用的代碼:我必須輸入一個日期

  1. ('2016年11月1日:

    CREATE FUNCTION fcBestFoodMonth(@date DATETIME) 
    RETURNS TABLE 
    AS 
    RETURN (SELECT TOP 10 m.Menu_Id, m.Menu_Name, COUNT(*) AS amount 
         FROM MENU_ORDER o 
         INNER JOIN MENU m 
         ON o.Menu_Id_Menu = m.Id_Menu 
         AND YEAR(p.Order_Date) = YEAR(@date) 
         AND MONTH(p.Order_Date) = MONTH(@date) 
         GROUP BY m.Menu_Id, m.Menu_Name 
         ORDER BY amount DESC) 
    
    -- Then I Call the function like this 
    SELECT * FROM dbo.fcBestFoodMonth(CAST('2016-11-01' AS datetime2)) 
    

    因此,有兩招我討厭這個「) 我希望我可以只輸入2串或數值類型,是一個月,一年

    喜歡的東西(」 2016' ,‘11’)或(2016,11)

  2. 我必須CAST日期參數。

    雖然我想打電話的功能簡單的像這樣:

    SELECT * FROM dbo.fcBestFoodMonth(param1, param2) 
    

回答

1

如果你的代碼是這樣的:

AND YEAR(p.Order_Date) = YEAR(@date) 
AND MONTH(p.Order_Date) = MONTH(@date) 

SQL Server將無法使用索引order_date的,因爲你在使用函數。您應該使用這樣的事情,而不是:

AND p.Order_Date >= @date 
AND p.Order_Date < dateadd(month, 1, @date) 

這裏假設你的@date變量總是包含月份的第一天。

你當然也可以構建從月份和年份的日期也一樣,如果你想要的,例如有:

set @date = convert(date, convert(varchar(4), @year) + '.' + 
      convert(varchar(2), @month) + '.01', 102) 
+0

你能告訴我應該在哪裏放語法=>'set @date = convert(....'?我不知道我應該在哪裏聲明'@ date'變量如果我使用'@ year'和'@ month'作爲參數 –

+0

如果你能向我展示代碼,我將不勝感激 –

+0

這是一個作爲變量的例子,但你當然可以在變量的地方使用它,因爲內聯函數只能有一個語句 –

2

如果您需要選擇基於月份和年份頻繁,也可能是有幫助的將這兩列作爲計算列添加到您的表定義中,並使它們保持,以便您可以對它們進行索引。

要添加計算列,使用T-SQL代碼:

ALTER TABLE dbo.Menu_Order 
ADD OrderMonth AS MONTH(Order_Date) PERSISTED; 

ALTER TABLE dbo.Menu_Order 
ADD OrderYear AS YEAR(Order_Date) PERSISTED; 

現在你的選擇可能會在WHERE子句中使用這兩個額外列:

SELECT TOP 10 
    m.Menu_Id, m.Menu_Name, COUNT(*) AS count 
FROM 
    MENU_ORDER o 
INNER JOIN 
    MENU m ON o.Menu_Id_Menu = m.Id_Menu 
      AND o.OrderYear = YEAR(@date) 
      AND o.OrderMonth = MONTH(@date) 
GROUP BY 
    m.Menu_Id, m.Menu_Name 
ORDER BY 
    count DESC 

隨着這些列堅持(實際上,實際存儲在磁盤上),你甚至可以將它們添加到索引,如果這會加快你的查詢。

由於您使用與月份和年份爲兩個表之間的連接從句沿Id_Menu,我可能會先試試這個指數:

CREATE NONCLUSTERED INDEX IX_Id_Month_Year 
    ON dbo.Menu_Order(Id_Menu, OrderMonth, OrderYear); 

,並看看是否有幫助這個查詢任何東西。

你的函數的簽名可以現在也可以更改爲:

CREATE FUNCTION fcBestFoodMonth(@OrderMonth INT, @OrderYear INT) 

,然後你可以在WHERE子句中使用這兩個int值進一步簡化您的查詢。