在我们的一个(C#)应用程序中,我们正在插入/更新一个大图(100个插入和更新)。这被包装在事务中,因为如果发生错误,我需要整个回滚。我们正在使用Dapper执行SQL语句。
不幸的是,整个操作目前需要2到8秒。这是数据库中核心表被锁定的2到8秒,这导致其他应用程序挂起或遭受锁定。
我确定插入到包含超过1.2亿条记录的表中的一项操作大部分时间都在占用,但是我不确定如何优化此操作。
大致而言,该表图的设置如下:
table A (
id int primary_key,
name nvarchar
)
table B (
id int primary_key,
a_id int foreign_key, # has an index
name nvarchar
)
将数据插入时,A我还需要将相应的数据插入B。因此,我scope_identity()用来获取记录的ID,并在将记录插入时使用它B。
伪明智地如下所示:
# open transaction
# perform other table inserts
#
# this is one of the slowest operations
for item in list_a
id_a = exec "insert into A (name) values (" + item.name + "); select scope_identity() as int"
for bar in item.list_b
exec "insert into B (id_a, name) values (" + id_a + ", " + bar.name + ")"
#
# perform more operations
# commit transaction
谷歌搜索时,解决方案之一是将其包装在事务中。但是我不知道性能如何,因为它已经包装在父事务中。它能解决问题吗?
通过使用插入记录来提供第二种解决方案union all select...,但是不知道我是否可以scope_identity()在该调用中使用。
我该如何改善这种情况?为了加快操作速度或防止其他应用程序遭受这些锁定,我还能做些其他事情吗?
梦里花落0921