Pergunta

Temos uma consulta que foge um bastante grande mesa que infelizmente precisa usar LIKE '% abc%' em um campo casal varchar para que o usuário pode pesquisar em nomes parciais, etc. SQL Server 2005

Será que a adição de um índice sobre estes campos varchar ajudar qualquer em termos de selecionar o desempenho da consulta quando utilizar LIKE ou ele basicamente ignorar os índices e fazer uma varredura completa nos casos?

Todas as outras formas possíveis para melhorar o desempenho ao utilizar COMO?

Foi útil?

Solução

Só se você adicionar pesquisa de texto completo para essas colunas, e usar os recursos de consulta de texto completo do SQL Server.

Caso contrário, não, um índice não vai ajudar.

Outras dicas

Você pode potencialmente ver melhorias de desempenho através da adição de índice (es), isso depende muito sobre as especificidades:)

Quanto do tamanho total da linha são as suas colunas baseiam? Quantas linhas que você espera para combinar? Você precisa retornar todas as linhas que correspondem ao predicado, ou apenas top 1 ou superior n linhas?

Se você está à procura de valores com alta seletividade / singularidade (tão poucas linhas para retornar), e as colunas predicados são uma parte pequeno de todo o tamanho da linha, um índice poderia ser bastante útil. Ele ainda será uma varredura, mas o seu índice vai caber mais linhas por página do que a tabela de origem.

Aqui está um exemplo onde o tamanho total da linha é muito maior do que o tamanho da coluna para pesquisar em:

create table t1 (v1 varchar(100), b1 varbinary(8000))
go
--add 10k rows of filler
insert t1 values ('abc123def', cast(replicate('a', 8000) as varbinary(8000)))
go 10000
--add 1 row to find
insert t1 values ('abc456def', cast(replicate('a', 8000) as varbinary(8000)))
go

set statistics io on 
go
select * from t1 where v1 like '%456%'
--shows 10001 logical reads

--create index that only contains the column(s) to search across
create index t1i1 on t1(v1)
go
select * from t1 where v1 like '%456%'
--or can force to 
--shows 37 logical reads

Se você olhar para o plano de execução real que você pode ver o motor de varredura do índice e fez uma pesquisa marcador na linha correspondente. Ou você pode dizer ao otimizador diretamente para usar o índice, se não tivesse decidir usar este plano por conta própria: seleccionar * de T1 com (índice (t1i1)) onde V1 como '% 456%'

Se você tem um monte de colunas para pesquisar em apenas alguns que são altamente seletiva, você pode criar vários índices e usar uma abordagem de redução. Por exemplo. primeiro determine um conjunto de IDs (ou qualquer que seja o seu PK é) do seu índice altamente seletivo, em seguida, procurar suas colunas menos seletivas com um filtro contra esse pequeno conjunto de PKs.

Se você sempre precisa retornar um grande conjunto de linhas que você quase certamente seria melhor fora com uma varredura da tabela.

Assim, os possíveis otimizações depender muito sobre as especificidades de sua definição da tabela e a seletividade de seus dados.

HTH! -Adrian

A única outra maneira (à excepção de usar a indexação de texto completo), você pode melhorar o desempenho é usar "COMO ABC%" - não adicione o curinga em ambas as extremidades de seu termo de busca - nesse caso, um índice poderia funcionar.

Se suas necessidades são tais que você tem que ter curingas em ambas as extremidades de seu termo de busca, você está fora de sorte ...

Marc

Like '% ABC%' irá sempre executar uma varredura completa da tabela. Não há maneira de contornar isso.

Você tem um par de abordagens alternativas. Em primeiro lugar pesquisa de texto completo, é realmente concebido para este tipo de problema, então eu olhar para isso em primeiro lugar.

Como alternativa, em algumas circunstâncias, pode ser apropriado para desnormalizar os dados e pré-processar os campos de destino em tokens apropriados, em seguida, adicione essas possíveis termos de busca em um separado para muitos tabela de pesquisa. Por exemplo, se os meus dados sempre consistiu em um campo contendo o padrão 'AAA / certificação / CCC' e meus usuários estavam procurando no BBB, então eu tokenizar que para fora em insert / update (e remover na deleção). Isso também seria um daqueles casos onde o uso de gatilhos, ao invés de código do aplicativo, seria muito preferido.

Eu devo ênfase que este não é realmente uma técnica ideal e só deve ser usado se os dados é um bom jogo para a abordagem e por algum motivo você não quer usar a pesquisa de texto completo (e o desempenho do banco de dados on similares varredura realmente é inaceitável). É também provável produzir dores de cabeça de manutenção mais baixo da linha.

criar estatísticas sobre essa coluna. sql server 2005 otimizou o em busca corda de modo que você pode se beneficiar disso.

Licenciado em: CC-BY-SA com atribuição
Não afiliado a StackOverflow
scroll top