SQL - 将MONTH提取从数字转换为完整月份名称

时间:2012-03-29 05:03:17

标签: sql sql-server

遇到特定存储过程的问题。我想我大概都是正确的...... 我基本上希望能够搜索一个月和一年,并在该时间线内出售任何产品的行。

CREATE PROCEDURE sp_products
    @productname    CHAR(20),
    @month      CHAR(9),
    @year           CHAR(4)


AS
SELECT  p.ProductName, 
        p.UnitPrice, 
        p.UnitsInStock,
        s.Name

FROM        Orders o
INNER JOIN  OrderDetails od
ON          o.OrderID = od.OrderID
INNER JOIN  Products p
ON          od.ProductID = p.ProductID
INNER JOIN  Suppliers s
ON          p.SupplierID = s.SupplierID 

WHERE   p.ProductName = @productname
AND     MONTH(o.OrderDate) = @month
AND     YEAR(o.OrderDate) = @year

给我一​​个“将varchar值'December'转换为数据类型int时转换失败。”错误。

以下是需要使用的查询:

EXEC sp_products '%tofu%', 'December', 1992

我想我知道自己需要做什么,只是不知道该怎么做...... 救命啊!

4 个答案:

答案 0 :(得分:1)

MONTH()返回一个int。

代替MONTH(o.OrderDate),尝试DATENAME(m,o.OrderDate)

编辑:

另请注意,如果不使用LIKE运算符,则使用通配符时输入将不会产生结果。

使用以下行更新您的程序:

WHERE p.ProductName LIKE @productname

答案 1 :(得分:1)

以下两个条件可能使您的查询不是sargable,因为在每种情况下,您都要将函数应用于要过滤的列:

AND     MONTH(o.OrderDate) = @month
AND     YEAR(o.OrderDate) = @year

我会改变它们:

SELECT     …
           …
           …

FROM       Orders o

/* this join actually replaces those two filters */
INNER JOIN (SELECT CAST('1-' + @month + CAST(-@year AS varchar(5))) AS Month) d
ON         o.OrderDate >= d.Month AND o.OrderDate < DATEADD(MONTH, 1, d.Month)

INNER JOIN … /* the rest of your joins */

WHERE      p.ProductName = @productname  /* only one condition here now */

也就是说,@year@month参数被格式化为可转换为表示相应月份的第一个的日期时间值的字符串,然后您正在使用此逻辑进行过滤:

order date >= the first of the given month
and
order date < the first of the next month after the given

当然,正如您已经被告知的那样,查询中的@productname过滤器应该使用LIKE比较而不是=,因为它似乎是您想要的通过掩码和特定名称进行搜索。所以WHERE子句看起来像这样:

WHERE      p.ProductName LIKE @productname

答案 2 :(得分:0)

要将月份字符串转换为月份的1-12表示,请使用内置函数DATENAME - 使用类似于1922年12月1日的内容重建日期,然后将其用于输入{{1} }

答案 3 :(得分:0)

由jlnorsworthy回答

&#34;而不是MONTH(o.OrderDate),尝试DATENAME(m,o.OrderDate)&#34;

这将有效

如果没有结果,请检查您传递的输入

EXEC sp_products &#39;%豆腐%&#39; ,&#39; 12月&#39;,1992

您正在将它与=运算符

进行比较
WHERE   p.ProductName = @productname

改变=喜欢它会起作用。