Suponha que eu tenha 2 tabelas, produtos e categorias de produtos. Ambas as tabelas têm relação no CategoryId. E esta é a consulta.
SELECT p.ProductId, p.Name, c.CategoryId, c.Name AS Category
FROM Products p
INNER JOIN ProductCategories c ON p.CategoryId = c.CategoryId
WHERE c.CategoryId = 1;
Quando crio o plano de execução, a tabela ProductCategories executa a busca de índice de cluster, que é a expectativa. Mas para a tabela Products, ele executa a verificação de índice de cluster, o que me faz duvidar. Por que o FK não ajuda a melhorar o desempenho da consulta?
Então, eu tenho que criar um índice em Products.CategoryId. Quando crio o plano de execução novamente, as duas tabelas executam a busca de índice. E o custo estimado da subárvore é bastante reduzido.
Minhas perguntas são:
Ao lado de FK ajuda na restrição de relacionamento, ela tem outra utilidade? Melhora o desempenho da consulta?
Devo criar um índice em todas as colunas do FK (como Products.CategoryId) em todas as tabelas?
fonte
Chaves estrangeiras podem melhorar (e prejudicar) o desempenho
Conforme declarado aqui: Chaves estrangeiras aumentam o desempenho
Você sempre deve criar índices nas colunas do FK para reduzir as pesquisas. O SQL Server não faz isso automaticamente.
Editar
Como o link agora parece estar inoperante (parabéns a Chris por perceber) , a seguir mostra a essência do motivo pelo qual as chaves estrangeiras podem melhorar (e prejudicar) o desempenho.
A chave estrangeira pode melhorar o desempenho
fonte
Uma chave estrangeira é um conceito de DBMS para garantir a integridade do banco de dados.
Quaisquer implicações / melhorias de desempenho serão específicas da tecnologia do banco de dados utilizada e são secundárias ao objetivo de uma chave estrangeira.
É uma boa prática no SQL Server garantir que todas as chaves estrangeiras tenham pelo menos um índice não clusterizado.
Espero que isso esclareça tudo, mas não hesite em solicitar mais detalhes.
fonte
Sua melhor aposta de desempenho é usar índices nos campos que você usa com frequência. Se você usa o SQL Server, pode usar o criador de perfil para criar um perfil em um banco de dados específico, pegar o arquivo que sai e usar o assistente de ajuste para receber recomendações sobre onde colocar seus índices. Também gosto de usar o profiler para liberar procedimentos armazenados de longa execução, tenho uma lista dos dez piores criminosos que publico todas as semanas, mantém as pessoas honestas: D.
fonte
Você pode usá-lo para ajudar a tornar uma consulta mais eficiente. Ele permite que você reestruture as consultas no SQL Server para usar uma associação externa em vez de uma interna, o que remove a necessidade de servidores sql de verificar se há um nulo na coluna. Você não precisa inserir esse qualificador porque o relacionamento de chave estrangeira já o impõe.
Então, é isso:
Torna-se isso:
Isso não necessariamente terá um desempenho enorme em consultas pequenas, mas quando as tabelas aumentam, pode ser mais eficiente.
fonte
Para o MySQL 5.7, ele definitivamente pode acelerar consultas envolvendo várias associações incrivelmente bem!
Usei o 'explicar' para entender minha consulta e descobri que estava juntando 4-5 tabelas - onde nenhuma chave era usada. Não fiz nada além de adicionar uma chave estrangeira a essas tabelas e o resultado foi uma redução de 90% no tempo de carregamento. As consultas que demoraram> 5s agora levam 500 ms ou menos.
Essa é uma melhoria ENORME!
E, como outros já mencionaram, você recebe o bônus adicional de garantir a integridade relacional.
Além disso, garantir a integridade referencial também traz seus próprios benefícios de desempenho. Ele tem o efeito de segunda ordem de garantir que as tabelas que possuem a chave estrangeira estejam 'atualizadas' com a tabela estrangeira. Digamos que você tenha uma tabela de usuários e uma tabela de comentários e faça algumas estatísticas na tabela de comentários. Provavelmente, se você excluir o usuário com força, também não deseja mais os comentários dele.
fonte
Adicionar uma chave estrangeira na tabela não melhorará o desempenho; basta dizer que, se você estiver inserindo um registro em um banco de dados da tabela ProductCategories, tentará descobrir que a coluna da chave estrangeira tem um valor que existe no valor da chave primária da tabela de produtos. A operação está sobrecarregada no banco de dados toda vez que você adiciona uma nova entrada na tabela ProductCategories. Portanto, adicionar uma chave estrangeira não melhorará o desempenho do banco de dados, mas cuidará da integridade do banco de dados. Sim, ele melhorará o desempenho do seu banco de dados se você estiver verificando a integridade usando chave estrangeira, em vez de executar muitas consultas para verificar se o registro existe no banco de dados do seu programa.
fonte
Não sei muito sobre o servidor SQL, mas no caso do Oracle, ter uma coluna de chave estrangeira reduz o desempenho do carregamento de dados. Isso ocorre porque o banco de dados precisa verificar a integridade dos dados para cada inserção. E sim, como já foi mencionado, ter um índice na coluna de chave estrangeira é uma boa prática.
fonte
A partir do SQL Server 2008, as chaves estrangeiras podem influenciar o desempenho, influenciando a maneira como o mecanismo de banco de dados escolhe otimizar a consulta. Consulte Heuristics Star Join no seguinte artigo: https://technet.microsoft.com/en-us/library/2008.04.04.dwperformance.aspx
fonte