我想选择一个定义为VARCHAR
的列,如下INTEGER
:
SELECT ID, CAST(Col1 as INT) as MyOutput FROM MyTABLE
问题是当列的格式无效(无法转换为整数)时我想将它们设置为NULL
。有没有办法在DB2中执行此操作?
答案 0 :(得分:5)
实现此目的的一种方法是编写自己的转换函数来处理格式异常,例如
create or replace function to_int_safe (str varchar(20))
returns int
deterministic
no external action contains sql
begin
declare continue handler for sqlstate '22018' -- on conversion error
return null;
return cast(str as int);
end
然后在您的查询中使用它:
SELECT ID, to_int_safe(Col1) as MyOutput FROM MyTABLE
答案 1 :(得分:0)
以下case语句确定字符串是否包含可以强制转换为整数的数字。它似乎工作到目前为止。然而,它复杂而且太长。我的意思是它只检查一个数字是否可以转换为整数,更不用说它是如何寻找十进制数字了。
select case when ( -- no leading sign
( instr(value,'-') = 0
and instr(value,'+') = 0 )
-- or one leading sign
or ( left(ltrim(value),1) in ('-','+')
and instr(ltrim(value),'-',2) = 0
and instr(ltrim(value),'+',2) = 0 ) )
-- no spaces between digits
and instr(trim(translate(value,'','+-')),' ') = 0
-- only numbers and sign
and length(trim(translate(value,'','+-0123456789'))) = 0
-- no empty strings
and length(trim(value)) <> 0
then cast(value as int)
else cast(null as int)
end
from table (
select '1 ' value from sysibm.sysdummy1
union all
select '1.' value from sysibm.sysdummy1
union all
select 'a' value from sysibm.sysdummy1
union all
select '+1' value from sysibm.sysdummy1
union all
select ' -1' value from sysibm.sysdummy1
union all
select '- 1' value from sysibm.sysdummy1
union all
select '--1' value from sysibm.sysdummy1
union all
select '1 1' value from sysibm.sysdummy1
union all
select '' value from sysibm.sysdummy1
union all
select ' ' value from sysibm.sysdummy1
union all
select cast(null as char) value from sysibm.sysdummy1
) string_numbers;
它也可以定义为函数。但是,这不会让它变得不那么难看。它可能会缩短或包含错误。因此,我更喜欢mustaccio的solution,即使他必须处理异常处理。