Я думаю, что следующий запрос по крайней мере приблизит вас. Он использует DMV, который был представлен в SQL Server 2014: sys.dm_exec_query_profiles (и спасибо Мартину Смиту за представление его мне через этот связанный DBA.StackExchange Ответ: Ход выполнения инструкции SELECT INTO :-).
Пожалуйста, обратите внимание:
!! Вам нужно будет добавить SET STATISTICS PROFILE ON;
или SET STATISTICS XML ON;
в пакете запроса , который делает CREATE INDEX
(и помещен перед тем в CREATE INDEX
заявлении, если это не было очевидно), еще ни одна строка не будет отображаться в этом DMV для этого ИСП / session_id
!!
IN
Оператор используется , чтобы отфильтровать Index Insert
строки , что, если он включен, приведет к увеличению TotalRows
значения, которые будут искажать расчеты , так как эта строка никогда не показывает каких - либо обработанных строк.
Отображаемое здесь количество строк (то есть TotalRows
) является двойным числом строк таблицы из-за операции, выполняемой в два этапа, каждый из которых работает со всеми строками: первый - «Сканирование таблицы» или «Сканирование кластерного индекса», а второй - «Сортировка». Вы увидите «Сканирование таблицы» при создании кластеризованного индекса или некластеризованного индекса в куче. Вы увидите «Сканирование кластеризованного индекса» при создании некластерного индекса в кластерном индексе.
Этот запрос не работает при создании отфильтрованных индексов. По какой-то причине отфильтрованные индексы а) не имеют шага «Сортировка», и б) row_count
поле никогда не увеличивается с 0.
Не уверен , что я испытывал раньше, но мои тесты теперь указывают , что отфильтрованных индексов будут захвачены этим запросом. Милая. Хотя остерегайтесь того, что число строк может быть выключено (я посмотрю, смогу ли я когда-нибудь это исправить).
При создании кластерного индекса в куче, в которой уже есть некластеризованные индексы, необходимо перестроить некластеризованные индексы (чтобы поменять RID - RowID - для ключа (ключей) кластерного индекса), и каждая перестройка некластерного индекса будет быть отдельной операцией и, следовательно, не отражаться в статистике, возвращаемой этим запросом при создании кластерного индекса.
Этот запрос был проверен на:
- Создание:
- Некластеризованные индексы в куче
- кластеризованный индекс (некластеризованных индексов не существует)
- Некластерные индексы в кластерном индексе / таблице
- кластерный индекс, когда некластерные индексы уже существуют
- Уникальные некластеризованные индексы в кластерном индексе / таблице
- Перестройка (таблица с кластеризованным индексом и одним некластеризованным индексом; протестирована на SQL Server 2014, 2016, 2017 и 2019) с помощью:
ALTER TABLE [schema_name].[table_name] REBUILD;
( при использовании этого метода отображается только кластерный индекс )
ALTER INDEX ALL ON [schema_name].[table_name] REBUILD;
ALTER INDEX [index_name] ON [schema_name].[table_name] REBUILD;
DECLARE @SPID INT = 51;
;WITH agg AS
(
SELECT SUM(qp.[row_count]) AS [RowsProcessed],
SUM(qp.[estimate_row_count]) AS [TotalRows],
MAX(qp.last_active_time) - MIN(qp.first_active_time) AS [ElapsedMS],
MAX(IIF(qp.[close_time] = 0 AND qp.[first_row_time] > 0,
[physical_operator_name],
N'<Transition>')) AS [CurrentStep]
FROM sys.dm_exec_query_profiles qp
WHERE qp.[physical_operator_name] IN (N'Table Scan', N'Clustered Index Scan',
N'Index Scan', N'Sort')
AND qp.[session_id] = @SPID
), comp AS
(
SELECT *,
([TotalRows] - [RowsProcessed]) AS [RowsLeft],
([ElapsedMS] / 1000.0) AS [ElapsedSeconds]
FROM agg
)
SELECT [CurrentStep],
[TotalRows],
[RowsProcessed],
[RowsLeft],
CONVERT(DECIMAL(5, 2),
(([RowsProcessed] * 1.0) / [TotalRows]) * 100) AS [PercentComplete],
[ElapsedSeconds],
(([ElapsedSeconds] / [RowsProcessed]) * [RowsLeft]) AS [EstimatedSecondsLeft],
DATEADD(SECOND,
(([ElapsedSeconds] / [RowsProcessed]) * [RowsLeft]),
GETDATE()) AS [EstimatedCompletionTime]
FROM comp;
Образец вывода:
Rows Percent Elapsed Estimated Estimated
CurrentStep TotalRows Processed RowsLeft Complete Seconds SecondsLeft CompletionTime
----------- --------- --------- -------- -------- ------- ----------- --------------
Clustered 11248640 4786937 6461703 42.56 4.89400 6.606223 2016-05-23
Index Scan 14:32:40.547
physical_operator_name
установленным наN'Index Scan'
, а неN'Table Scan'
илиN'Clustered Index Scan'
. Кроме того, он будет очень медленным, так как он выполнит несколько поисков RID.ALTER INDEX ALL
и даже (частично)ALTER TABLE .. REBUILD
. Пожалуйста ознакомтесь :-).