2009-05-28 10 views

risposta

23

È possibile controllare questo abbastanza facilmente controllando i piani di query in entrambe le situazioni. Non c'è alcuna differenza di cui io sia a conoscenza. C'è una differenza logica tra BETWEEN e "<" e ">" ... TRA è compreso. È equivalente a "< =" e "=>".

+0

Buon punto. Una sottigliezza che non avevo notato. –

1

I due operatori che vengono confrontati tra loro qui sono fondamentalmente diversi e, quindi, perché i piani di esecuzione che vengono generati sono anche probabilmente diversi (anche se non garantiti).

Il fattore determinante è la distribuzione dei dati (selettività) della colonna a cui sono applicati gli operatori di confronto. Questo insieme con le statistiche determinerà se un indice è o non è utilizzato, ecc.

Spero che questo abbia senso.

+0

Non so esattamente perché questo è stato votato. John ha detto qualcosa di sbagliato? Qualcuno non si sente molto bene? Qualcuno ha qualche idea? – wcm

+0

Non ho mai modificato la domanda originale. Inoltre non ho votato. –

+0

questa risposta ha senso per me ... quindi questo voto negativo è strano – Michael

0

in realtà. Cerco solo di verificare tra alcuni dei miei dati. TRA È equivalente a "> =" e "<". Ad esempio: tra '05/01/2010 'e '05/30/2010': riceverai dati solo tra il 5/1/2010 00:00:00 e il 29/05/2010 alle 23:59:59. Prova a interrogare la tua tabella con "Ordina per [TimeField] desc" e vedrai il risultato.

+3

No, questo non è corretto. Sei sicuro di avere dati che sono esattamente '30/05/2010 00: 00: 00.000' al millisecondo? –

+0

Ciò contraddice la documentazione, il che significa che se questo è vero è un bug. Tendo ad essere d'accordo con il signor Smith sul fatto che probabilmente i dati sono sbagliati. –

0

Mi interessava anche sapere se c'è una differenza di prestazioni quando ho usato (> = e < =) rispetto all'utilizzo della parola chiave between. (Vengo da uno sfondo dotnet e come gli operatori di stile> =).
Ecco lo script che ho usato:

DECLARE 
    @Startdatetime datetime , 
    @Diff int = 0 , 
    @Addrowcount int = 1000; 

SET NOCOUNT ON; 

--Create a tempory table to perform our tests on 

CREATE TABLE dbo.perftest(id smallint NOT NULL 
             IDENTITY(1 , 1) 
             PRIMARY KEY , 
          mytext nvarchar(50)NOT NULL); 

--Now add some sample rows 

SET @Addrowcount = 1000; 

WHILE(@Addrowcount > 0) 

    BEGIN 

     INSERT INTO dbo.perftest(mytext) 
     VALUES('thetext'); 

     SET @Addrowcount = @Addrowcount - 1; 

    END; 

SELECT @Startdatetime = GETDATE(); 

-- do method 1 here 

SELECT mytext 
    FROM dbo.perftest 
    WHERE(id >= 100) 
    AND (id <= 900); 

--end method1 

SELECT @Diff = DATEDIFF(millisecond , @Startdatetime , GETDATE()); 

PRINT ':Method 1: ' + CAST(@Diff AS nvarchar(20)) + ' ms'; 

--reset start time 

SELECT @Startdatetime = GETDATE(); 

--do method2 here 

SELECT mytext 
    FROM dbo.perftest 
    WHERE id BETWEEN 100 
    AND 900; 

--end method2 

SELECT @Diff = DATEDIFF(millisecond , @Startdatetime , GETDATE()); 

PRINT ':Method 2: ' + CAST(@Diff AS nvarchar(20)) + ' ms'; 

I risultati sono stati:

Metodo 1: 140 ms

Metodo 2: 70 ms

Così sembra che le prestazioni sono migliorate usando tra.

+0

Non sei sicuro di quanto sia valido un test come questo ... Suppongo sia valido come qualsiasi semplice test di profilo, ma questo non sta dicendo molto. Può essere molto diverso in base al caching (hai appena aggiunto i record) e non succede nient'altro al momento (a differenza di un server del mondo reale), e tutti i record vengono aggiunti contemporaneamente, rispetto alla frammentazione su più pagine/tempo . – eselk

1

L'amore quando le persone danno il codice per eseguire i test, è necessario eseguire un test secondario più ampio/ripetuto per tenere conto degli indici caricati in memoria, ecc. Prima di saltare alle conclusioni. Qui è lo stesso codice con un tavolo più grande e 10 iterazioni

DECLARE 
    @Startdatetime datetime , 
    @Diff int = 0 , 
    @Addrowcount int = 1000 , 
    @ptr int = 1; 


SET NOCOUNT ON; 

--Create a tempory table to perform our tests on 
DROP TABLE dbo.perftest 

CREATE TABLE dbo.perftest(id int NOT NULL 
             IDENTITY(1 , 1) 
             PRIMARY KEY , 
          mytext nvarchar(50)NOT NULL); 

--Now add some sample rows 

SET @Addrowcount = 20000; 

WHILE(@Addrowcount > 0) 

    BEGIN 

     INSERT INTO dbo.perftest(mytext) 
     VALUES('thetext'); 

     SET @Addrowcount = @Addrowcount - 1; 

    END; 

WHILE @ptr < 10 -- do this a few times to account for indexes being loaded into memory 

BEGIN 

    SELECT @Startdatetime = GETDATE(); 

    -- do method 1 here 

    SELECT mytext 
     FROM dbo.perftest 
     WHERE(id >= (100 + (@ptr * 1000))) 
     AND (id <= (500 + (@ptr * 1000))); 

    --end method1 

    SELECT @Diff = DATEDIFF(millisecond , @Startdatetime , GETDATE()); 

    PRINT ':Method 1: ' + CAST(@Diff AS nvarchar(20)) + ' ms'; 

    --reset start time 

    SELECT @Startdatetime = GETDATE(); 

    --do method2 here 

    SELECT mytext 
     FROM dbo.perftest 
     WHERE id BETWEEN (300 + (@ptr * 1000)) 
     AND (800 + (@ptr * 1000)); 

    --end method2 

    SELECT @Diff = DATEDIFF(millisecond , @Startdatetime , GETDATE()); 

    PRINT ':Method 2: ' + CAST(@Diff AS nvarchar(20)) + ' ms'; 

    SET @ptr = @ptr + 1 

END 

ti dà un insieme molto diverso di risultati:

--Method 1 -- 10 ms 
--Method 2 -- 33 ms 
--Method 1 -- 40 ms 
--Method 2 -- 26 ms 
--Method 1 -- 23 ms 
--Method 2 -- 23 ms 
--Method 1 -- 13 ms 
--Method 2 -- 16 ms 
--Method 1 -- 13 ms 
--Method 2 -- 20 ms 
--Method 1 -- 6 ms 
--Method 2 -- 16 ms 
--Method 1 -- 26 ms 
--Method 2 -- 16 ms 
--Method 1 -- 13 ms 
--Method 2 -- 13 ms 
--Method 1 -- 16 ms 
--Method 2 -- 13 ms 

direi da questo (ancora piuttosto non scientifica) di prova, non molta differenza in entrambi i casi.

4

motore La query converte tra in >= e <= (dare un'occhiata al piano di query) quindi, in pratica, sono identici e in teoria >= <= è più veloce perché il motore non dovrà tradurre. Buona fortuna notando una differenza però.

Io uso tra ogni caso, trovo si legge più facile

query

molto complessi/viste nidificate con numerosi tra i confronti potrebbe trarre beneficio dal cambiamento in >= <= come questo potrebbe potenzialmente prevenire i timeout di ottimizzazione, riducendo il tempo speso per il refactoring query (solo una teoria, non testata da me & non l'ho mai notato)

Problemi correlati