2012-03-27 13 views
18

Questa è probabilmente una semplice clausola where, ma voglio dire, da Columnx (che è datetime) Voglio tutte le righe in cui solo l'anno 2010. =SQL select * from colonna in cui l'anno = 2010

così:

select * from mytable where Columnx = 
+0

qualche informazione in più: http://stackoverflow.com/questions/7870943/how-efficient-is-the-yeardate-function – Simon

risposta

26
select * from mytable where year(Columnx) = 2010 

Per quanto riguarda l'utilizzo degli indici (segreteria commento di Simon):

se si dispone di un indice su Columnx, SQLServer volontà non utilizzarlo se si utilizza la funzione "anno" (o qualsiasi altra funzione).

Esistono due soluzioni possibili, uno esegue la ricerca per intervallo come Columnx> = '01012010' e Columnx < = '31122010' e un altro è per creare una colonna calcolata con l'espressione year (Columnx), indicizzarlo, e poi fare il filtro in questa nuova colonna

+0

Se le prestazioni non sono all'altezza, penso che questo metodo non faccia uso di alcun indice sulla colonna 'Columnx' – Simon

+1

@simon - Hai ragione, il wrapping di una colonna in una funzione lo rende non-sargabile. Ciò si traduce in una scansione completa. Non lo farei mai. È una pratica molto scarsa per le date di filtraggio. Consiglio vivamente l'OP guarda la tua risposta. – MatBailie

+0

Ciao @simon, grazie per il tuo commento, ho aggiunto ulteriori spiegazioni in merito. Non l'ho fatto prima perché poiché l'OP ha problemi molto semplici con una funzione Year(), non immaginavo che a questo punto si sarebbe preoccupato dell'uso degli indici. – Diego

5

T-SQL e altri;

select * from t where year(Columnx) = 2010 
+3

Wrapping una colonna in una funzione rende non sargable . Ciò si traduce in una scansione completa. Non lo farei mai. È una pratica molto scarsa per le date di filtraggio. Consiglio vivamente che l'OP guardi alla risposta @simon. – MatBailie

21

se capisco che si desidera tutte le righe per l'anno 2010, poi:

select * 
    from mytable 
where Columnx >= '2010-01-01 00:00:00' 
     and Columnx < '2011-01-01 00:00:00' 
+2

+1 - Fa quello che l'OP vuole *** e *** fa uso di indici per una ricerca di distanza, che possono essere ordini di grandezza più veloci rispetto alle altre risposte qui finora. – MatBailie

+3

Sì, +1 per consentire l'uso di indici.Si potrebbe anche semplificare la condizione a: 'dove Columnx> = '2010-01-01' e Columnx <'2011-01-01'' (senza alcuna differenza di efficienza, solo alcuni caratteri di codice in meno :) –

1

suo solo semplice

select * from myTable where year(columnX) = 2010 
+1

Wrapping a la colonna in una funzione lo rende non sargabile. Ciò si traduce in una scansione completa. Non lo farei mai. È una pratica molto scarsa per le date di filtraggio. Consiglio vivamente che l'OP guardi alla risposta @simon. – MatBailie

0

NB: Se volete l'anno per essere basato su una data di riferimento, il codice qui sotto calcola le date per il between dichiarazione:

declare @referenceTime datetime = getutcdate() 
select * 
from myTable 
where SomeDate 
    between dateadd(year, year(@referenceTime) - 1900, '01-01-1900')      --1st Jan this year (midnight) 
    and dateadd(millisecond, -3, dateadd(year, year(@referenceTime) - 1900, '01-01-1901')) --31st Dec end of this year (just before midnight of the new year) 

Allo stesso modo, se si sta utilizzando un valore di anno, scambiando year(@referenceDate) per la vostra il valore dell'anno di riferimento lavorerà

declare @referenceYear int = 2010 
select * 
from myTable 
where SomeDate 
    between dateadd(year,@referenceYear - 1900, '01-01-1900')      --1st Jan this year (midnight) 
    and dateadd(millisecond, -3, dateadd(year,@referenceYear - 1900, '01-01-1901')) --31st Dec end of this year (just before midnight of the new year) 
Problemi correlati