为什么CONVERT中的比较不起作用?

时间:2012-01-06 02:36:35

标签: sql sql-server-2008

是否可以在CONVERT或CAST函数中使用比较运算符?

我的声明如下:

SELECT
    ...
    CASE field
        WHEN 'Y' THEN 1  # If Y then True
        ELSE 0           # Anything else is False
    END
    ...
FROM ...

类似的事情发生在一些领域,所以我想把它改成更短的版本:

SELECT
    ...
    CONVERT(BIT, field = 'Y')
    ...
FROM ...

但MSSQL发出错误Incorrect syntax near '='.

我对帮助的解释是它应该有效:

  • CONVERT ( data_type [ ( length ) ] , expression [ , style ] )
  • expression: expression { binary_operator } expression
  • binary_operator:是一个运算符,它定义了两个表达式组合以产生单个结果的方式。 binary_operator可以是算术运算符,赋值运算符(=),按位运算符,比较运算符,逻辑运算符,字符串连接运算符(+)或一元运算符。
  • comparison operator: ( = | > | < | >= | <= | <> | != | !< | !> )

我进行了一些测试并获得了这些结果:

SELECT CONVERT(BIT, 0)       // 0
SELECT CONVERT(BIT, 1)       // 1
SELECT CONVERT(BIT, 1+2)     // 1
SELECT CONVERT(BIT, 1=2)     // Error
SELECT CONVERT(BIT, (1=2))   // Error
SELECT CONVERT(BIT, (1)=(2)) // Error

1 个答案:

答案 0 :(得分:4)

我认为你误解了CONVERT的文档。 CONVERT的文档中没有任何内容表明它将处理一个使用比较运算符的表达式,只是它接受一个表达式。事实证明CONVERT不处理每个有效的SQL表达式。至少它无法处理使用比较运算符的表达式的结果。

如果您查看Operators的文档,您会看到比较运算符(在这种情况下,您想要的=)返回Boolean数据类型,并在WHERE子句和控制流语句中使用。从运营商的文档:

  

比较运算符的结果具有布尔数据类型,它具有三个值:   TRUE,FALSE和UNKNOWN。返回布尔数据类型的表达式称为   布尔表达式。

     

与其他SQL Server数据类型不同,不能使用布尔数据类型   指定为表列或变量的数据类型,而不能   在结果集中返回。

     

...

     

在WHERE子句中使用带有布尔数据类型的表达式   过滤符合搜索条件且符合条件的行   控制流语言语句,如IF和WHILE ......

这有助于解释为什么像SELECT 1=2这样的SQL是无效的SQL,因为它会创建一个带有Boolean数据类型的结果集,文档中说这是不允许的。这也解释了为什么CASE WHEN构造是必要的,因为它可以评估比较运算符并返回SQL Server可以在结果集中返回的数据类型的单个值。

此外,如果您查看CONVERT的文档,您会发现BooleanCAST不支持CONVERT(请参阅在页面中间,那里没有Boolean数据类型。

出于您的目的,我认为您使用的是CASE WHEN。如果它有帮助你可以在一行上写下来:

CASE WHEN field = 'Y' THEN 1 ELSE 0 END

或者,您可以创建一个UDF来处理CASE表达式(类似dbo.func_DoCase(field, 'Y', 1, 0)),但我个人只会坚持使用CASE WHEN