事务中的SELECT可以锁定表吗?
我想知道如果一个表在一个事务中,它是否有可能阻塞一个表。
它是这样的:
CREATE PROCEDURE InsertClient (@name NVARCHAR(256))
AS
BEGIN
DECLARE @id INT = 0;
BEGIN TRY
BEGIN TRAN InsertingClient
SELECT @id = MAX(ID) + 1 FROM Clients;
INSERT INTO Clients (Id, Name)
VALUES (@id, @name);
SELECT id, name
FROM Clients;
COMMIT TRAN InsertingClient
END TRY
BEGIN CATCH
ROLLBACK TRAN InsertingClient
END CATCH;
END
这是一个虚拟示例,但是如果该表中有很多记录,并且 API 正在接收大量请求并调用此存储过程,那么初始和最终选择可能会阻止吗?我应该只在插入中使用开始和提交来避免阻塞吗?
谢谢!
回答
根据示例代码你只要是至关重要的第一选择是因为它似乎要手动创建一个基于该表中的最大ID的ID,并没有锁定,你可以用重复结束了该表的事务中。假设您的实际代码有一些锁定提示(例如with (updlock,holdlock))来确保这一点。
但是,您的第二个选择不应该在您的事务中,因为它所做的只是使事务中较早获得的锁持续选择的额外时间,当(再次基于示例代码)没有必要这样做时.
顺便说一句,有更好的方法来生成 id,例如使用identity列。