Tenho uma tabela com a seguinte estrutura:
ItemID int
ItemType char(1)
Language char(2)
Localization char(2)
Literal nvarchar(4000)
que é usado para traduzir o texto de específico ItemID
para Literal
um. A Literal
coluna pode conter HTML
tags. Para um conjunto específico de consultas, essas HTML
tags precisam ser removidas e, como a sanitização é feita com SQL CLR em milhares de linhas, prefiro não executá-la na leitura.
Então, eu adicionei uma coluna persistente como esta:
ALTER TABLE [dbo].[table]
ADD [LiteralSanitized] AS NULLIF(CAST(LTRIM(RTRIM([dbo].[fn_Utils_RemoveAllHtmlTags] ([Literal]))) AS NVARCHAR(4000)), '') PERSISTED;
A tabela tem apenas um índice (a chave primária) com a seguinte definição:
ItemID, ItemType, Language, Localization
Portanto, a consulta foi mais rápida, mas estou vendo algumas leituras adicionais para esta tabela:
Scan count - 2 vs 12,230
Logical reads - 3,234 vs 43,472
o que pode ser normal, pois agora estou lendo mais dados por causa da coluna. Então, eu adicionei o seguinte índice:
(ItemID ASC, ItemType ASC, Language ASC, Localization ASC) INCLUDE ([LiteralSanitized])
mas não é usado pelo motor. Então, eu tento forçar o motor a usá-lo:
UPDATE #temp
SET [QuestionText] = PSGQ.[LiteralSanitized]
FROM #temp PQD
INNER JOIN [dbo].[table_with_translations] PSGQ WITH(INDEX = [the_new_index])
ON PQD.[ProtoQuestionID] = PSGQ.[ItemID]
WHERE PSGQ.[ItemType] = 'Q'
AND PSGQ.[Language] = @language
AND RTRIM(PSGQ.[Localization]) = ''
AND PSGQ.[LiteralSanitized] IS NOT NULL;
mas o motor está fazendo o seguinte:
- executa a varredura de índice (no meu novo índice)
- em seguida, executa o loop aninhado e a pesquisa de chave com o índice clusterizado
- extrair a
literal
coluna
Se minha coluna for Persisted
, por que o motor continua tentando devolver a Literal
coluna já que ela nem é necessária?
A resposta mais provável para sua pergunta está nesta postagem de blog de Paul White: Colunas computadas adequadamente persistentes
Parece muito com o SQL Server decidiu que prefere recalcular o valor da coluna em vez de lê-lo do disco.
Uma solução, conforme mencionado por Paul, é usar o sinalizador de rastreamento 176 para desabilitar a expansão da coluna computada.