2013-07-25 38 views
1

我正在使用SQL Server 2005.如何从SQL查询中的NVARCHAR列中选择整数值?

我试图获得值为fk_unitserial是整数。该列被定义为nvarchar(255), not null

认为我在此列中选择数值,并确定这些值使用下面的查询是在一个特定的范围:

select t.pkid, t.fk_unitserial 
from (
    select r.pkid, r.fk_unitserial 
    from tbl_ovenresults r 
    where isnumeric(r.fk_unitserial + '.0e0') = 1 
) t 
where convert(decimal(38, 0), t.fk_unitserial) between -2147483648 and 2147483647 
order by t.pkid 

但运行它给我的留言:

Msg 8114, Level 16, State 5, Line 1 
Error converting data type nvarchar to numeric. 

看起来像违规值是129896545820,但运行

select convert(decimal(38, 0), 129896545820) 

按预期工作。

我错过了什么?

编辑

我想我要问的,也许,是如果ISNUMERIC以往任何时候都不能在CONVERT(DECIMAL(38, 0), value)一起使用的值返回1

+0

违规值肯定不是129896545820,因为我使用nvarchar列类型创建了示例表,并且提到的值和查询运行正常。数字值之间必须有一些字符或空格。 – Sonam

+0

@Sonam - 对于使用我的'CONVERT'方法无法转换的值,ISNUMERIC'会返回'1'吗? – ken

+0

我不这么认为,Isnumeric肯定会返回0,因为在上述条件下不能转换的值。 – Sonam

回答

1

SQL Server保留重新排列表达式的权利,但case声明除外。这意味着您可能会将不合格的值从子查询传递到外部查询。

有一个例外是case声明,其中通常遵循顺序评估(当涉及汇总表达式时存在星号,但这不是问题)。我会建议:

select r.pkid, r.fk_unitserial 
from tbl_ovenresults r 
where (case when r.fk_unitserial not like '[^0-9]' then convert(decimal(38, 0), t.fk_unitserial) end) 
      between -2147483648 and 2147483647 
order by t.pkid; 

作为一个说明。 isnumeric的表达式将返回值为'-'的值。

+0

诀窍。但是,在你的例子中,“不喜欢”应该是“like”吗? – ken

+0

@ken。 。 。不。表达式是说“列不像一个不包含数字的模式”。好吧,这没有意义。这实际上是说“在列中只有数字”。 –