转换时SQL转换失败

Posted

技术标签:

【中文标题】转换时SQL转换失败【英文标题】:SQL conversion failed when converting 【发布时间】:2014-05-15 09:20:53 【问题描述】:

以下情况:

xy 列定义为 varchar(25)。在视图(SQL Server Mgmt Studio 2008)中,我过滤了所有带有字母的值(-> 不像 '%[A-Z]%')并将其转换为 int(cast(xy as int))。

如果我现在尝试对该列进行比较(例如 xy

提前感谢您的帮助...

这行得通(它过滤出例如值'G8111'): 选择单位 FROM CD_UNITS 作为 INNER JOIN DEF_STATION AS b ON a.STATION = b.STATION WHERE (b.CURENT = 'T') 和 UNID like '%[A-Z]%'

但是当我把它放在一个视图中时,一个 make select 就可以了:

select * from my_view where xy

系统提示“将 varchar 值 'G8111' 转换为数据类型 int 时转换失败。”但是应该在上面的查询中过滤掉“G8111”...

【问题讨论】:

您的过滤器仅适用于字母;您的数据中是否有其他字符(如逗号或其他标点符号)不会转换为 int?另外,您的过滤器是大写的;应该是小写过滤的值吗? 它会更具可读性,如果您可以使用查询生成视图本身来编辑您的问题 您可能想阅读并投票SQL Server should not produce illogical errors 抱歉 - 删除了上一条评论,没想到。更好的过滤器是 WHERE ISNUMERIC(value) = 1 然后你至少保证它的数字(尽管可能仍然在 int 的范围之外) ISNUMERIC(value)=1 是毫无意义的检查,因为正如您所说,将接受无法转换为 int 的值,包括 £ 本身和 0d0 这样的宝石。跨度> 【参考方案1】:

优化器有时会执行crazy things,因此尽管“内部”过滤器1“应该”保护您,但优化器仍可能将转化率推低至低于过滤器并导致此类错误。

它不会这样做的唯一半记录的地方是CASE expression:

CASE 语句(sic) 按顺序评估其条件,并在满足条件的第一个条件处停止。在某些情况下,在 CASE 语句接收表达式结果作为其输入之前计算表达式。

...

您应该只依赖于标量表达式(包括返回标量的非相关子查询)的 WHEN 条件的评估顺序,而不是聚合表达式

所以目前唯一可行的方法是:

CASE WHEN xy NOT LIKE '%[^0-9]%' THEN CONVERT(int,xy) END < 1000

这还使用了带有LIKE 的双重否定,以确保它仅在值仅包含数字时尝试转换。


1无论是在子查询、CTE、视图中,还是仅仅考虑SELECTWHERE 子句中的logical processing order。在单个查询中,优化器可以并将转换操作推过过滤器。

【讨论】:

以上是关于转换时SQL转换失败的主要内容,如果未能解决你的问题,请参考以下文章

SQL查询错误:转换varchar值时转换失败

从 C# 中的字符串 SQL 转换日期和/或时间时转换失败

SQL 异常:将 nvarchar 值“[anyvalue]”转换为数据类型 int 时转换失败

将 XML 文件导入 SQL Server 时唯一标识符转换失败

将 C# 日期时间发送到 SQL Server - 错误“从字符串转换日期和/或时间时转换失败”

查看数据转换失败 - SQL Server