Condividi tramite


Informazioni sugli hash join

Gli hash join prevedono due tipi di input, ovvero input di creazione e input probe. Query Optimizer assegna all'input più piccolo il ruolo di input di creazione.

Gli hash join vengono utilizzati per vari tipi di operazioni di corrispondenza tra set, ovvero inner join, outer join sinistro, destro e completo, semi-join sinistro e destro, intersezione, unione e differenza. Una variante dell'hash join può inoltre eseguire la rimozione dei duplicati e il raggruppamento, ad esempio SUM(salary) GROUP BY department. Queste modifiche utilizzano un solo input sia per il ruolo di creazione che per il ruolo probe.

Nelle sezioni seguenti vengono descritti i diversi tipi di hash join: hash join in memoria, grace hash join e hash join ricorsivo.

Hash join in memoria

L'hash join esegue in primo luogo la scansione o il calcolo dell'intero input di creazione, quindi crea una tabella hash in memoria. Ogni riga viene inserita in un hash bucket in base al valore hash calcolato per la chiave hash. Se l'intero input di creazione è inferiore alla memoria disponibile, tutte le righe possono essere inserite nella tabella hash. A questa fase di creazione segue la fase probe. Vengono eseguiti la scansione o il calcolo dell'intero input probe, una riga alla volta. Per ogni riga probe viene calcolato il valore della chiave hash, la scansione dell'hash bucket corrispondente e vengono prodotte le corrispondenze.

Grace hash join

Se le dimensioni dell'input di creazione sono superiori a quelle della memoria disponibile, l'hash join viene eseguito in vari passaggi. In questo caso, l'hash join viene definito grace hash join. Ogni passaggio prevede una fase di creazione e una fase probe. L'input di creazione e l'input probe vengono inizialmente analizzati e partizionati in più file, tramite una funzione di hashing sulle chiavi hash. L'utilizzo della funzione di hashing sulle chiavi hash garantisce che ogni coppia di record su cui si basa il join si trovi nella stessa coppia di file. In tal modo il join di due input di grandi dimensioni risulta convertito in istanze multiple di dimensioni ridotte della stessa attività. L'hash join viene quindi applicato a ogni coppia di file partizionati.

Hash join ricorsivo

Se l'input di creazione ha dimensioni tali per cui gli input per un'unione esterna standard richiedono più livelli di unione, saranno necessari più passaggi di partizionamento e più livelli di partizionamento. Se soltanto alcune partizioni sono di grandi dimensioni, i passaggi di partizionamento aggiuntivi vengono utilizzati soltanto per tali partizioni. Per velocizzare al massimo i passaggi di partizionamento vengono utilizzate operazioni di I/O asincrone di grandi dimensioni, per cui un unico thread può tenere occupate più unità disco.

[!NOTA]

Se l'input di creazione non ha dimensioni di molto superiori a quelle della memoria disponibile, gli elementi dell'hash join in memoria e del grace hash join vengono combinati in un unico passaggio, producendo un hash join ibrido.

Durante l'ottimizzazione non sempre è possibile determinare il tipo di hash join che verrà utilizzato. Pertanto, SQL Server utilizza inizialmente un hash join in memoria, quindi passa gradualmente a grace hash join e hash join ricorsivo a seconda delle dimensioni dell'input di creazione.

Se Query Optimizer non prevede correttamente quale dei due input è il più piccolo, al quale quindi deve essere assegnato il ruolo di input di creazione, i ruoli di input di creazione e di input probe vengono invertiti dinamicamente. L'hash join utilizza comunque come input di creazione il file di overflow più piccolo. Questa tecnica è detta inversione dei ruoli. L'inversione dei ruoli si verifica all'interno dell'hash join dopo l'esecuzione di almeno uno spill sul disco.

[!NOTA]

L'inversione dei ruoli si verifica in maniera indipendente da qualsiasi struttura o hint per la query e inoltre non viene visualizzata nel piano di query. Quando si verifica, l'inversione dei ruoli è un'operazione trasparente all'utente.

Hash bailout

Il termine hash bailout è talvolta utilizzato per descrivere grace hash join o hash join ricorsivo.

[!NOTA]

Gli hash join ricorsivi e gli hash bailout causano una riduzione delle prestazioni del server. Se si nota la presenza di molti eventi Hash Warning in una traccia, aggiornare le statistiche sulle colonne su cui si basa il join.

Per ulteriori informazioni sugli hash bailout, vedere Classe di evento Hash Warning.