Ваш код не очень понятен относительно того, как и почему механизм требуется и работает.
Однако при условии, что у вас должно быть несколько записей с непогашенным балансом, и что вы должны рассматривать несколько записей последовательно как частьэтого механизма, тогда у вас есть два варианта решения этого в SQL (обработка в клиентском коде - другой вариант):
1) Используйте курсор, как вы сделали
2) Используйте временныйтаблицу или табличную переменную и итерируйте по ней - очень похоже на курсор, но, возможно, быстрее - вам нужно попробовать и посмотреть, например:
declare @TableVariable table (Cost money, RemainingQty int, Id int, OrderBy int, Done bit default(0))
declare @Id int, @Cost money, @RemainingQty int
insert into @TableVariable (Cost, RemainingQty, Id, OrderBy)
SELECT
itembalance.Cost
, itembalance.RemainingQty
, itembalance.Id
, 1 /* Some order by condition */
FROM dbo.itembalance
WHERE itembalance.ItemID = @v_item_to_be_updated AND RemainingQty > 0
while exists (select 1 from @TableVariable where Done = 0) begin
select top 1 @Id = id, @Cost = Cost, @RemainingQty
from @TableVariable
where Done = 0
order by OrderBy
-- Do stuff here
update @TableVariable set Done = 1 where id = @Id
end
Однако код, который вы показали, не кажется, что он долженбыть медленным - возможно, вам не хватает соответствующих индексов и что одно обновление ItemId блокирует слишком много строк в таблице ItemBalance, что затем влияет на другие обновления ItemId.