我正在编写一个T-SQL存储过程,使用语句
插入表中INSERT INTO [tableName]
.....
SELECT * FROM [tableName]
有时输入表(SELECT)可能包含错误的值:插入期望小数的表,而select返回NVarChar值,这将导致转换错误。 现在因为语句执行了“批量插入”,我不知道插入的最后一条记录是什么,或者包含错误数据的记录是什么。 SQL只说“转换错误.....” 有没有办法“记录”最后插入的记录,以便至少我知道什么行包含错误的值? (不使用游标)
答案 0 :(得分:5)
观察此查询的结果
SELECT
v.id,
v.val,
x=TRY_CAST(v.val AS DECIMAL(28,2))
FROM
(VALUES(1,'1.26'),(2,'A.13')) AS v(id,val)
WHERE
TRY_CAST(v.val AS DECIMAL(28,2)) IS NULL
结果:
+----+------+------+
| id | val | x |
+----+------+------+
| 2 | A.13 | NULL |
+----+------+------+
它使用TRY_CAST
,如果NULL
失败,则返回CAST
。您可以使用它来确定失败的记录,或缩小您插入目标表的集合。
答案 1 :(得分:2)
没有上一个错误。
根据基本的数据库ACID条件,语句是ATOMIC - 它完全可以工作或完全失败。还没有在内部处理行的已定义顺序 - 这可能因服务器和数据特征而异。
通常在将数据复制到目标表之前清理数据。
答案 2 :(得分:1)
您可以尝试使用 OUTPUT
子句输出插入的行,直到遇到错误为止。您还可以使用 ORDER BY
,以便更快地确定哪个是插入失败的下一行。然后,知道失败的行,应该更容易确定问题的字段。
具有OUTPUT子句的UPDATE,INSERT或DELETE语句 即使语句遇到错误,也会将行返回给客户端 回滚。如果发生任何错误,则不应使用该结果 你运行声明。
答案 3 :(得分:1)
您可以在下面的语句中使用哪个列进行转换问题。
SELECT SQL_VARIANT_PROPERTY(col1, 'BaseType') from Table1
过滤问题
SELECT * from Table1 WHERE QL_VARIANT_PROPERTY(col1, 'BaseType') not like 'decimal%'
答案 4 :(得分:1)
我曾经在表中导入了1500万行时遇到过这个问题。我们最终决定采用以下方法在SSIS中做得最好:
稍后当SSIS完成时,我们将分析所有失败的记录。这样我们就可以说你在1500万只中只有5条错误记录,我们会在隔离表中成功地插入1499995条记录和5条记录。
谢谢并希望这种方法有所帮助