2009-11-09 15 views
7

Sto provando a mettere insieme una query che visualizzerà un record specifico (trovato dall'ID primario del record) nella parte superiore e visualizzerà tutti gli altri record sottostanti, ordinato per data (ho "data_added" come uno dei campi nella tabella, oltre all'ID principale).SQL per avere un record specifico nella parte superiore, tutti gli altri sotto

Potrei farlo con UNIONE (la prima selezione individuerebbe il record che desidero, e l'altra selezione visualizzerà tutti gli altri record), ma mi chiedo se c'è forse un modo migliore?

Sto utilizzando Oracle, a proposito.

risposta

17

È possibile farlo di classificare da due campi

Il primo sarebbe un'espressione che restituisce 0 se la riga è quello che si desidera o 1 se esso isn 't. Il ordinamento sarà crescente in modo da ottenere prima il record preferito.

Il secondo campo di ordinamento sarebbe datato_adeguato in modo che i record rimanenti siano ordinati in questo ordine.

paura non so Oracle in SQL Server che sarebbe qualcosa di simile

select * 
from the_table 
order by (case id when 999 then 0 else 1 end), date_added desc 
+0

Grazie per la risposta. Che cosa significa "ordina per 0", a proposito? Ho notato che non posso usarlo da solo, ad es. solo "ORDINA PER 0". (Vengo visualizzato l'errore: "L'articolo ORDER BY deve essere il numero di un'espressione dell'elenco SELECT") – Dario

+1

'ORDINE DI ' ha un significato speciale in Oracle, verrà ordinato all'ennesima colonna. Ovviamente non c'è mai una colonna 0. Con CASE, aggiungerà una nuova colonna a ogni riga e ordinerà su quella. La nuova colonna sarà 1 per la chiave primaria corrispondente e 0 ovunque. – Andomar

1

Non so esattamente Oracle, ma si potrebbe forse fare qualcosa di simile ..

ORDER BY IF(id == THE_ID, 0, 1), date_added 
+0

+1 Non sono sicuro che Oracle supporti IF in questo modo! – Andomar

+0

Oracle non supporta IIF, ma puoi 'DECODE (id, THE_ID, 0,1)' invece – Andomar

7

Un modo più semplice sarebbe un ordine di fantasia dal costrutto. Ecco un esempio per pk = 123:

select * 
from YourTable 
order by case when yourpk = 123 then 1 else 2 end, date_added 
+0

questo metterebbe il record specifico fino alla fine, dovrebbe essere "... then 1 else 2 end ..." –

+0

@ammoQ: Grazie, risposta modificata (reko_t ha pubblicato la stessa idea prima) – Andomar

-1

Il modo più semplice sarebbe quella di riconoscere che si desidera visualizzare due cose separate e quindi scrivere a separare le query semplici. Una query per recuperare il primo record e il secondo per recuperare l'elenco ordinato. Non c'è un reale vantaggio in termini di prestazioni nel fare qualcosa di più di questo a causa di un unico record.

+0

Sì, ma ci sono dei vantaggi nel farlo come una singola istruzione SQL. Alcuni ambienti (ad esempio suite di reporting) non consentono un facile riutilizzo dei costrutti SQL, quindi potrebbe dover ripetere la maggior parte degli SQL due volte, il che è problematico per la manutenzione. Inoltre, farlo in SQL è più consace :-). – sleske

0
SELECT * 
FROM `Table` 
ORDER BY (`id` = THE_ID) DESC, `date_added` DESC 
0

È possibile ordinare più di un record verso l'alto utilizzando la stessa tecnica

999 prima 998 secondi seguito da tutto il resto ordinato per data

select *

from the_table 
order by (case id when 999 then 0 when 998 then 1 else 2 end), date_added desc 
Problemi correlati