SQL Server 2000 & # 8220; NESSUN PREDICATO DI PARTECIPAZIONE & # 8221; avvertimento: perché?

StackOverflow https://stackoverflow.com/questions/290885

  •  08-07-2019
  •  | 
  •  

Domanda

Ho uno strano problema con SQL Server 2000 e non riesco proprio a pensare ad una ragione per cui ciò accada.

Esistono due tabelle, entrambe con una chiave primaria combinata con un indice cluster su di essa, entrambe le chiavi hanno la stessa struttura:

(VARCHAR(11), INT, DATETIME)   /* can't change this, so don't suggest I should */

Quindi, unirsi a loro in questo modo è abbastanza facile:

SELECT t1.Foo, t2.Bar
FROM   table1 t1 INNER JOIN table2 t2 ON t1.VarcharKey = t2.VarcharKey
WHERE  t1.VarcharKey = 'Foo'

Guardando il piano di esecuzione della query, vedo questo:

  • Ricerca nell'indice cluster [db]. [dbo]. [tabella1]. [PK_table1] (48%)
  • Ricerca indice cluster [db]. [dbo]. [tabella2]. [PK_table2] (51%)
  • Nested Loops (Inner Join) (1%) Avvertenza: NO JOIN PREDICATE
  • Seleziona (0%)

Ora, se lo faccio (nota la stringa NVARCHAR!):

SELECT t1.Foo, t2.Bar
FROM   table1 t1 INNER JOIN table2 t2 ON t1.VarcharKey = t2.VarcharKey
WHERE  t1.VarcharKey = N'Foo'

Ottengo:

  • Scansione indice cluster [db]. [dbo]. [tabella1]. [PK_table1] (98%)
  • Ricerca indice cluster [db]. [dbo]. [tabella2]. [PK_table2] (1%)
  • Nested Loops (Inner Join) (1%) nessun avviso qui
  • Seleziona (0%)

Questo comportamento mi lascia un po 'perplesso.

  • Perché esiste un " NO JOIN PREDICATE " avviso e perché scompare quando cambio 'Foo' in N'Foo '? Le mie colonne chiave non sono di tipo NVARCHAR, quindi questo non dovrebbe fare alcuna differenza, o dovrebbe?
  • La presenza di questo avviso ha implicazioni negative o posso ignorarlo?
  • Perché passa da una ricerca indice a una scansione indice?

Alcune informazioni di base: la cardinalità della tabella è di ca. 25.000 registrazioni una tabella, ca. 12.000 record nell'altro. Il livello di compatibilità del database è 80 (SQL Server 2000) le regole di confronto predefinite sono SQL_Latin1_General_CP1_CI_AS , se questo fa alcuna differenza.

Ecco il contenuto di @@ VERSION :

  

Microsoft SQL Server 2000 - 8.00.2273 (Intel X86) 7 marzo 2008 22:19:58 Copyright (c) 1988-2003 Microsoft Corporation Enterprise Edition su Windows NT 5.0 (Build 2195: Service Pack 4)

PS: sono a conoscenza di KB322854 , ma ovviamente non lo è.

È stato utile?

Soluzione

  

Perché passa da una ricerca indice   a una scansione dell'indice?

Questa è in gran parte un'ipotesi, ma qui va:

Nel primo caso ('Foo'), MSSQL riconosce che il valore da cercare è una corrispondenza perfetta per la prima parte dell'indice su t1, e quindi utilizza l'indice per trovare un record in t1 (Ricerca indice, possibilmente una ricerca binaria). Avendo trovato un record in t1 che ha un indice che corrisponde perfettamente a t2, può usare l'indice per trovare i record in t2.

Nel secondo caso, (N'Foo '), MSSQL riconosce che NON ha una corrispondenza perfetta tra l'indice e il valore cercato, quindi non può usare l'indice come indice, ma deve fare una tabella completa scansione. Tuttavia, poiché l'indice contiene le informazioni necessarie (in una forma diversa) ed è più piccolo della tabella completa, può eseguire una scansione completa dell'indice come se fosse la tabella (Questo è più veloce della scansione della tabella, poiché meno pagine deve essere letto per il disco; tuttavia, sembra impiegare circa 90 volte più tempo della ricerca dell'indice)

Altri suggerimenti

Da SqlServerCentral :

le query possono avere quella che sembra una condizione di join perfettamente formata. Ma quando si esamina il piano di query, verrà visualizzato un avviso che indica "Nessun predicato di join" che indica che 2 delle tabelle coinvolte non hanno un predicato (una volta unito). L'aggiunta di un'opzione (Force Order) alla query produce un piano completamente diverso e l'avviso scompare (in alcuni casi). Ecco come sai che questo è il problema. La maggior parte delle query che ho visto funzionare meglio su SQL 2000 presentano questo problema. L'aggiornamento cumulativo 4 a SP 2 dovrebbe risolvere il problema.

Autorizzato sotto: CC-BY-SA insieme a attribuzione
Non affiliato a StackOverflow
scroll top