SQL中varchar类型Manager_ID去除小数部分转换报错解决方案
问题描述
我有一个追加查询,其中Manager_ID字段为varchar(250)类型,原值例如为31.0,我需要对该值做转换,仅输出'31',删除小数点后的所有内容。我尝试使用Convert和Cast函数转换为integer或nvarchar类型均未成功,持续收到如下报错:
将varchar值'31.0'转换为数据类型int时转换失败
我调整过插入目标表和数据源表的字段类型,仍未解决问题。
执行convert(int, convert(decimal(9,2),[Manager_ID]))的报错信息:
将varchar数据类型转换为numeric时出错
原始查询代码
INSERT INTO [dbo].[tblUsers] ( [User_ID] ,[FirstName] ,[LastName] ,[FullName] ,[EMail] ,[UserRoles] ,[PostionType] ,[ManagerID] ,[UUID] ,[External_UUID] ,[home_Location_id] ,[Home_Organization_ID] ,[Record_types] ,[Location_Ceiling_ID] ,[Organization_Ceiling_ID] ,[Payroll_Identifier] ,[Created_Date] ,[Created_Time] ,[Update_Date] ,[Update_Time]) Select id-- User_ID ,first_name ,last_name ,full_name ,email ,role_id --UserRoles ,position --PositionType ,cast(Manager_id as nvarchar(10)) as ManagerID ,uuid ,external_uuid ,home_location_id ,home_organization_id ,[type] --Record_Types ,location_ceiling_id ,organization_ceiling_id ,payroll_identifier ,Left(Convert(varchar(20), created_at, 120),10) as Create_Date ,Right(convert(varchar(16), created_at, 120),5) as Create_Time ,left(Convert(varchar(20), updated_at, 120),10) as Update_Date ,Right(convert(varchar(16), updated_at, 120),5) as Update_Time from [stg].[Users]
问题原因
Manager_ID为字符串类型,字段中存在非标准数值格式的脏数据,比如空格、特殊字符、空值或格式异常的内容,导致转换为数值类型时直接报错。
最终解决方案
无需将字符串转换为数值类型,直接通过字符串操作截取小数点前的内容,规避脏数据导致的转换报错:
,SUBSTRING(manager_id, 1, CASE WHEN CHARINDEX('.',manager_id) - 1 < 0 THEN LEN(manager_id) ELSE CHARINDEX('.',manager_id) - 1 END) as ManagerID
逻辑说明:
- 用
CHARINDEX查找小数点在字符串中的位置 - 若没有小数点,直接返回完整字符串
- 若存在小数点,截取小数点之前的所有字符即可得到目标结果
内容的提问来源于stack exchange,提问作者Karen Schaefer
相关产品推荐
相关产品推荐

