我按以下方式将数据加载到表中:
DECLARE @srcRc INT;
DECLARE @dstRc INT;
SET @srcRc = ( SELECT COUNT(*) FROM A )
INSERT INTO t
(Col1
,Col2
,Col3
)
SELECT A.Col1
,A.Col2
,B.Col3
FROM A
JOIN B
ON A.Id = B.Id;
SET @dstRc = @@ROWCOUNT
现在我正在比较变量@srcRc
和@dstRc
。 ROWCOUNT
必须相同。如果不是,则需要删除插入的行。
Q1:回滚插入行的最佳策略是什么?
我有几个想法:
1)如果rowcount不匹配,则在事务和回滚中运行load
2)将标志列(位)添加到名为toBeDeleted
的目标表中,运行加载,如果rowcount不匹配,请更新toBeDeleted
列1
值以将其标记为候选删除。然后在批处理模式下删除(while循环)。
或者不删除它们,但在使用t
表时始终从查询中排除删除候选项
3)在插入行之前,首先比较行计数。如果不匹配,请不要开始加载。
DECLARE @srcRc INT;
DECLARE @dstRc INT;
SET @srcRc = ( SELECT COUNT(1) FROM A );
SET @dstRc = ( SELECT COUNT(1) FROM A JOIN B ON A.Id = B.Id );
Q2:对于更高的行数,更好的解决方案,比如10-100 mil。? 问题3:或者类似案例有更好的策略吗?
答案 0 :(得分:0)
好的,假设:
当表A和B的内容可能已更改
时,您需要在稍后的某个日期工作在T中可能还有其他行,您不想将其作为回滚的一部分删除。
然后你必须保留一个你插入的行的列表,因为你无法从A和B中可靠地重新生成该列表而你不能删除T中的所有内容
你可以用两种方式做到这一点
更改您的导入,以便首先将行插入导入表格,让导入表格保持不变,直到您确定不再需要它为止。
在T [importId]中添加一个额外的列,您可以在其中添加唯一标识值
显然,第一种策略使用了更多的磁盘空间。因此,保留数据的时间越长,数据越多,额外列的外观就越好。
另一种选择是单独生成导入数据列表,并将事务sql作为批量插入,将所有数据硬编码到sql中。
这适用于小型列表,初始设置数据等。
编辑:
从你的评论中听起来你不想要回滚本身。但是围绕导入过程应用业务逻辑的最佳方式。
在这种情况下,你的第三个答案是最好的。当您知道源数据不正确时,请不要进行导入。