【问题标题】:how to insert data into multiple relational tables by using multiple tasks如何使用多个任务将数据插入到多个关系表中
【发布时间】:2014-08-06 12:17:23
【问题描述】:
首先,我是编程新手。
我正在尝试制作一个使用许多任务的程序。这些任务会将数据插入到多个关系表中。 (我使用的是 sql server)
但是,我认为可能存在并发问题,例如,当一个任务将数据插入第一个表并使用最后插入的身份 ID 时,在另一个关系表中,同时另一个任务可以将数据插入第一个表并更改最后插入的身份 id,所以在这种情况下,当最后插入的身份 id 更改时,第一个任务将使用错误的(由第二个任务更改)最后插入的身份 id,我猜。
我想使用可序列化的锁来锁定整个事务,我想这会起作用,但我猜这也会影响性能。
那么,在不影响性能的情况下,我应该怎么做呢?
【问题讨论】:
标签:
sql
sql-server
transactions
database-concurrency
【解决方案1】:
作为一名程序员,您需要担心的主要是在正确范围的 TRANSACTION 中进行更改。只要你这样做,你应该没问题。如果您的数据库管理员更改了默认隔离级别,则可能会出现问题,但这种情况非常罕见。
基本格式是
BEGIN TRANSACTION AddUser
INSERT INTO Table1 ...
INSERT INTO Table2 ...
...
COMMIT TRANSACTION AddUser
AddUser 是你想出的名字
如果您这样做,DBMS 将以确保正确结果的最有效方式正确锁定表。好吧,从并发的角度来看是正确的,您的逻辑可能仍然不正确:-)
编辑:注意:新程序员有时会犯的一个错误是在可能导致中断的操作中打开 TRANSACTION。在打开事务之前收集所有输入,不要开始,写一张表,询问用户要做什么,然后写第二张表并提交。如果用户去吃午饭或程序崩溃,这会锁定您的桌子!
【解决方案2】:
INSERT 语句分配的IDENTITY 值可用于SCOPE_IDENTITY()。在多行INSERT 的情况下,OUTPUT 子句可用于返回每个插入行的IDENTITY 值。这些是每个连接的范围,因此每个任务的第一个插入返回的IDENTITY 值在默认的READ_COMMITTED 隔离级别中将是不同的,并且可用于将相关行随后插入到后续表中。