Изоляция SNAPSHOT может только уменьшить (некоторые) взаимные блокировки, связанные с чтением, но она абсолютно ничего не делает, чтобы избежать взаимных блокировок записи и записи. Если вы генерируете более 100 000 строк в час, что составляет ~ 30 операций вставки в секунду, сканирование при удалении почти наверняка конфликтует с другими операциями записи. Если все, что вы делаете, это Вставка, никогда не обновлять, тогда блок удаления, но не тупик при блокировке на уровне строки, но так как таблица достаточно велика и удаление выполняет сканирование, движок, скорее всего, выберет блокировку страницы для удаления, следовательно, вероятно, тупик, который вы получите.
без индекса на входной дате, при удалении которого нет выбора, кроме как сканировать всю таблицу. Такого рода таблицы, которые часто вставляются вверху и удаляются внизу, на самом деле являются очередями, и вы должны организовать их по дате входа. Это означает, что entrydate , вероятно, должен быть крайним левым ключом в кластерном индексе . Эта организация допускает четкое разделение вставок, встречающихся на одном конце таблицы, и удалений, встречающихся на другом конце. Но это довольно радикальное изменение, особенно если вы используете statvalueid для чтения этих значений. Я предполагаю, что сейчас у вас есть кластеризованный индекс, основанный на поле автоинкремента (StatValueId). Также я предполагаю, что entrydate и statvalueid взаимосвязаны. Если оба предположения верны, то вы должны удалить базу don statvalueid: найти самый большой идентификатор, который можно удалить, а затем удалить все в кластерном индексе слева от этого идентификатора:
declare @statvalueidmax int;
select @statvalueidmax = max(statvalueid)
from statvalue with (readpast)
where entrydate < dateadd(minute,-60, getdate());
delete statvalue
where statvalueid <= @statvalueidmax;
Я сделал ряд предположений, они могут быть ошибочными. Но суть идеи заключается в том, что вы должны отделить вставки от удалений, чтобы они не перекрывались.