ORDER BY CLAUSE

The ORDER BY clause allows users to sort a result set prior to it being returned. It is perhaps the most straightforward clause among the BIG SIX because of users’ experiences using the popular spreadsheet software, Microsoft Excel. Like the sorting functionality afforded to users of Microsoft Excel, the ORDER BY clause permits users to sort result sets in ascending or descending order based on the values of one or more user-specified attributes. To illustrate the use of the ORDER BY clause, I will walk through a few examples. Following a few examples highlighting the clause’s basic usage, I’ll showcase a couple of additional examples aiming to explore the possible things a result set can be sorted by. Additionally, I will introduce a method to implement custom sorting and highlight how missing values are handled.

Before reading further, consider reviewing the Example Data section below to familiarize yourself with the data being used throughout the examples on this page. If you are already familiar with the data, then skip to the Basic Usage section.

Example Data
The schemas, corresponding tables, and data used in the example problems can be found at livesql.oracle.com. To more easily follow the examples covered on this page, consider first reading the table descriptions below and reviewing each table’s contents. To review the data maintained in each table, click on the icon next to the table name. To hide the data, click the icon again.

hr.employees
Contains information related to each employee and a hierarchal employee-manager relationship. There is one row per employee.
employee_idfirst_namelast_nameemailphone_numberhire_datejob_idsalarycommission_pctmanager_iddepartment_id
100StevenKingSKING515.123.456717-Jun-03AD_PRES2400090
101NeenaKochharNKOCHHAR515.123.456821-Sep-05AD_VP1700010090
102LexDe HaanLDEHAAN515.123.456913-Jan-01AD_VP1700010090
103AlexanderHunoldAHUNOLD590.423.45673-Jan-06IT_PROG900010260
104BruceErnstBERNST590.423.456821-May-07IT_PROG600010360
105DavidAustinDAUSTIN590.423.456925-Jun-05IT_PROG480010360
106ValliPataballaVPATABAL590.423.45605-Feb-06IT_PROG480010360
107DianaLorentzDLORENTZ590.423.55677-Feb-07IT_PROG420010360
108NancyGreenbergNGREENBE515.124.456917-Aug-02FI_MGR12008101100
109DanielFavietDFAVIET515.124.416916-Aug-02FI_ACCOUNT9000108100
110JohnChenJCHEN515.124.426928-Sep-05FI_ACCOUNT8200108100
111IsmaelSciarraISCIARRA515.124.436930-Sep-05FI_ACCOUNT7700108100
112Jose ManuelUrmanJMURMAN515.124.44697-Mar-06FI_ACCOUNT7800108100
113LuisPoppLPOPP515.124.45677-Dec-07FI_ACCOUNT6900108100
114DenRaphaelyDRAPHEAL515.127.45617-Dec-02PU_MAN1100010030
115AlexanderKhooAKHOO515.127.456218-May-03PU_CLERK310011430
116ShelliBaidaSBAIDA515.127.456324-Dec-05PU_CLERK290011430
117SigalTobiasSTOBIAS515.127.456424-Jul-05PU_CLERK280011430
118GuyHimuroGHIMURO515.127.456515-Nov-06PU_CLERK260011430
119KarenColmenaresKCOLMENA515.127.456610-Aug-07PU_CLERK250011430
120MatthewWeissMWEISS650.123.123418-Jul-04ST_MAN800010050
121AdamFrippAFRIPP650.123.223410-Apr-05ST_MAN820010050
122PayamKauflingPKAUFLIN650.123.32341-May-03ST_MAN790010050
123ShantaVollmanSVOLLMAN650.123.423410-Oct-05ST_MAN650010050
124KevinMourgosKMOURGOS650.123.523416-Nov-07ST_MAN580010050
125JuliaNayerJNAYER650.124.121416-Jul-05ST_CLERK320012050
126IreneMikkilineniIMIKKILI650.124.122428-Sep-06ST_CLERK270012050
127JamesLandryJLANDRY650.124.133414-Jan-07ST_CLERK240012050
128StevenMarkleSMARKLE650.124.14348-Mar-08ST_CLERK220012050
129LauraBissotLBISSOT650.124.523420-Aug-05ST_CLERK330012150
130MozheAtkinsonMATKINSO650.124.623430-Oct-05ST_CLERK280012150
131JamesMarlowJAMRLOW650.124.723416-Feb-05ST_CLERK250012150
132TJOlsonTJOLSON650.124.823410-Apr-07ST_CLERK210012150
133JasonMallinJMALLIN650.127.193414-Jun-04ST_CLERK330012250
134MichaelRogersMROGERS650.127.183426-Aug-06ST_CLERK290012250
135KiGeeKGEE650.127.173412-Dec-07ST_CLERK240012250
136HazelPhiltankerHPHILTAN650.127.16346-Feb-08ST_CLERK220012250
137RenskeLadwigRLADWIG650.121.123414-Jul-03ST_CLERK360012350
138StephenStilesSSTILES650.121.203426-Oct-05ST_CLERK320012350
139JohnSeoJSEO650.121.201912-Feb-06ST_CLERK270012350
140JoshuaPatelJPATEL650.121.18346-Apr-06ST_CLERK250012350
141TrennaRajsTRAJS650.121.800917-Oct-03ST_CLERK350012450
142CurtisDaviesCDAVIES650.121.299429-Jan-05ST_CLERK310012450
143RandallMatosRMATOS650.121.287415-Mar-06ST_CLERK260012450
144PeterVargasPVARGAS650.121.20049-Jul-06ST_CLERK250012450
145JohnRussellJRUSSEL011.44.1344.4292681-Oct-04SA_MAN140000.410080
146KarenPartnersKPARTNER011.44.1344.4672685-Jan-05SA_MAN135000.310080
147AlbertoErrazurizAERRAZUR011.44.1344.42927810-Mar-05SA_MAN120000.310080
148GeraldCambraultGCAMBRAU011.44.1344.61926815-Oct-07SA_MAN110000.310080
149EleniZlotkeyEZLOTKEY011.44.1344.42901829-Jan-08SA_MAN105000.210080
150PeterTuckerPTUCKER011.44.1344.12926830-Jan-05SA_REP100000.314580
151DavidBernsteinDBERNSTE011.44.1344.34526824-Mar-05SA_REP95000.2514580
152PeterHallPHALL011.44.1344.47896820-Aug-05SA_REP90000.2514580
153ChristopherOlsenCOLSEN011.44.1344.49871830-Mar-06SA_REP80000.214580
154NanetteCambraultNCAMBRAU011.44.1344.9876689-Dec-06SA_REP75000.214580
155OliverTuvaultOTUVAULT011.44.1344.48650823-Nov-07SA_REP70000.1514580
156JanetteKingJKING011.44.1345.42926830-Jan-04SA_REP100000.3514680
157PatrickSullyPSULLY011.44.1345.9292684-Mar-04SA_REP95000.3514680
158AllanMcEwenAMCEWEN011.44.1345.8292681-Aug-04SA_REP90000.3514680
159LindseySmithLSMITH011.44.1345.72926810-Mar-05SA_REP80000.314680
160LouiseDoranLDORAN011.44.1345.62926815-Dec-05SA_REP75000.314680
161SarathSewallSSEWALL011.44.1345.5292683-Nov-06SA_REP70000.2514680
162ClaraVishneyCVISHNEY011.44.1346.12926811-Nov-05SA_REP105000.2514780
163DanielleGreeneDGREENE011.44.1346.22926819-Mar-07SA_REP95000.1514780
164MatteaMarvinsMMARVINS011.44.1346.32926824-Jan-08SA_REP72000.114780
165DavidLeeDLEE011.44.1346.52926823-Feb-08SA_REP68000.114780
166SundarAndeSANDE011.44.1346.62926824-Mar-08SA_REP64000.114780
167AmitBandaABANDA011.44.1346.72926821-Apr-08SA_REP62000.114780
168LisaOzerLOZER011.44.1343.92926811-Mar-05SA_REP115000.2514880
169HarrisonBloomHBLOOM011.44.1343.82926823-Mar-06SA_REP100000.214880
170TaylerFoxTFOX011.44.1343.72926824-Jan-06SA_REP96000.214880
171WilliamSmithWSMITH011.44.1343.62926823-Feb-07SA_REP74000.1514880
172ElizabethBatesEBATES011.44.1343.52926824-Mar-07SA_REP73000.1514880
173SunditaKumarSKUMAR011.44.1343.32926821-Apr-08SA_REP61000.114880
174EllenAbelEABEL011.44.1644.42926711-May-04SA_REP110000.314980
175AlyssaHuttonAHUTTON011.44.1644.42926619-Mar-05SA_REP88000.2514980
176JonathonTaylorJTAYLOR011.44.1644.42926524-Mar-06SA_REP86000.214980
177JackLivingstonJLIVINGS011.44.1644.42926423-Apr-06SA_REP84000.214980
178KimberelyGrantKGRANT011.44.1644.42926324-May-07SA_REP70000.15149
179CharlesJohnsonCJOHNSON011.44.1644.4292624-Jan-08SA_REP62000.114980
180WinstonTaylorWTAYLOR650.507.987624-Jan-06SH_CLERK320012050
181JeanFleaurJFLEAUR650.507.987723-Feb-06SH_CLERK310012050
182MarthaSullivanMSULLIVA650.507.987821-Jun-07SH_CLERK250012050
183GirardGeoniGGEONI650.507.98793-Feb-08SH_CLERK280012050
184NanditaSarchandNSARCHAN650.509.187627-Jan-04SH_CLERK420012150
185AlexisBullABULL650.509.287620-Feb-05SH_CLERK410012150
186JuliaDellingerJDELLING650.509.387624-Jun-06SH_CLERK340012150
187AnthonyCabrioACABRIO650.509.48767-Feb-07SH_CLERK300012150
188KellyChungKCHUNG650.505.187614-Jun-05SH_CLERK380012250
189JenniferDillyJDILLY650.505.287613-Aug-05SH_CLERK360012250
190TimothyGatesTGATES650.505.387611-Jul-06SH_CLERK290012250
191RandallPerkinsRPERKINS650.505.487619-Dec-07SH_CLERK250012250
192SarahBellSBELL650.501.18764-Feb-04SH_CLERK400012350
193BritneyEverettBEVERETT650.501.28763-Mar-05SH_CLERK390012350
194SamuelMcCainSMCCAIN650.501.38761-Jul-06SH_CLERK320012350
195VanceJonesVJONES650.501.487617-Mar-07SH_CLERK280012350
196AlanaWalshAWALSH650.507.981124-Apr-06SH_CLERK310012450
197KevinFeeneyKFEENEY650.507.982223-May-06SH_CLERK300012450
198DonaldOConnellDOCONNEL650.507.983321-Jun-07SH_CLERK260012450
199DouglasGrantDGRANT650.507.984413-Jan-08SH_CLERK260012450
200JenniferWhalenJWHALEN515.123.444417-Sep-03AD_ASST440010110
201MichaelHartsteinMHARTSTE515.123.555517-Feb-04MK_MAN1300010020
202PatFayPFAY603.123.666617-Aug-05MK_REP600020120
203SusanMavrisSMAVRIS515.123.77777-Jun-02HR_REP650010140
204HermannBaerHBAER515.123.88887-Jun-02PR_REP1000010170
205ShelleyHigginsSHIGGINS515.123.80807-Jun-02AC_MGR12008101110
206WilliamGietzWGIETZ515.123.81817-Jun-02AC_ACCOUNT8300205110
oe.orders
For each order placed by a customer, various attributes are captured. There is one row per order.
order_idorder_dateorder_modecustomer_idorder_statusorder_totalsales_rep_idpromotion_id
245816-AUG-07 03.34.12.234359 PMdirect101078279.6153
239719-NOV-07 02.41.54.696211 PMdirect102142283.2154
245402-OCT-07 05.49.34.678340 PMdirect10316653.4154
235414-JUL-08 06.18.23.234567 PMdirect104046257155
235808-JAN-08 05.03.12.654278 PMdirect10527826155
238114-MAY-08 08.59.08.843679 PMdirect106323034.6156
244031-AUG-07 09.53.06.008765 PMdirect107370576.9156
235708-JAN-06 08.19.44.123456 PMdirect108559872.4158
239410-FEB-08 09.22.35.564789 PMdirect109521863158
243502-SEP-07 11.22.53.134567 PMdirect144662303159
245520-SEP-07 11.34.11.456789 AMdirect145714087.5160
237916-MAY-07 02.22.24.234567 AMdirect146817848.2161
239602-FEB-06 01.34.56.345678 AMdirect147834930161
240629-JUN-07 04.41.20.098765 AMdirect14882854.2161
243413-SEP-07 05.49.30.647893 AMdirect1498268651.8161
243602-SEP-07 06.18.04.378034 AMdirect11686394.8161
244627-JUL-07 07.03.08.302945 AMdirect1178103679.3161
244727-JUL-08 08.59.10.223344 AMdirect101833893.6161
243214-SEP-07 09.53.40.223345 AMdirect1021010523163
243313-SEP-07 10.19.00.654279 AMdirect1031078163
235526-JAN-06 09.22.51.962632 AMonline104894513.5
235626-JAN-08 09.22.41.934562 AMonline105529473.8
235908-JAN-06 09.34.13.112233 PMonline10695543.1
236014-NOV-07 12.22.31.223344 PMonline1074990.4
236113-NOV-07 01.34.21.986210 PMonline1088120131.3
236213-NOV-07 02.41.10.619477 PMonline109492829.4
236323-OCT-07 05.49.56.346122 PMonline144010082.3
236428-AUG-07 06.18.45.942399 PMonline14549500
236528-AUG-07 07.03.34.003399 PMonline146927455.3
236628-AUG-07 08.59.23.144778 PMonline147537319.4
236727-JUN-08 09.53.32.335522 PMonline14810144054.8
236826-JUN-08 10.19.43.190089 PMonline1491060065
236926-JUN-07 11.22.54.009932 PMonline116011097.4
237027-JUN-08 12.22.11.647398 AMonline1174126
237116-MAY-07 01.34.56.113356 AMonline118679405.6
237227-FEB-07 12.22.33.356789 AMonline119916447.2
237327-FEB-08 01.34.51.220065 AMonline1204416
237427-FEB-08 02.41.45.109654 AMonline12104797
237526-FEB-07 03.49.50.459233 AMonline1222103834.4
237607-JUN-07 06.18.08.883310 AMonline123611006.2
237707-JUN-07 07.03.01.001100 AMonline141538017.8
237824-MAY-07 08.59.10.010101 AMonline142525691.3
238016-MAY-07 09.53.02.909090 AMonline143327132.6
238214-MAY-08 10.19.03.828321 AMonline144871173
238312-MAY-08 11.22.30.545103 AMonline145836374.7
238412-MAY-08 12.22.34.525972 PMonline146329249.1
238508-DEC-07 11.34.11.331392 AMonline1474295892
238606-DEC-07 12.22.34.225609 PMonline1481021116.9
238711-MAR-07 03.34.56.536966 PMonline149552758.9
238804-JUN-07 04.41.12.554435 PMonline1504282694.3
238904-JUN-08 05.49.43.546954 PMonline151417620
239018-NOV-07 04.18.50.546851 PMonline15297616.8
239127-FEB-06 05.03.03.828330 PMdirect153248070.6156
239221-JUL-07 08.59.57.571057 PMdirect154926632161
239310-FEB-08 07.53.19.528202 PMdirect155423431.9161
239502-FEB-06 08.19.11.227550 PMdirect156368501163
239819-NOV-07 09.22.53.224175 PMdirect15797110.3163
239919-NOV-07 10.22.38.340990 PMdirect158025270.3161
240010-JUL-07 01.34.29.559387 AMdirect159269286.4161
240110-JUL-07 02.22.53.554822 AMdirect1603969.2163
240202-JUL-07 03.34.44.665170 AMdirect1618600154
240301-JUL-07 04.49.13.615512 PMdirect1620220154
240401-JUL-07 04.49.13.664085 PMdirect1636510158
240501-JUL-07 04.49.13.678123 PMdirect16451233159
240729-JUN-07 07.03.21.526005 AMdirect16592519155
240829-JUN-07 08.59.31.333617 AMdirect1661309158
240929-JUN-07 09.53.41.984501 AMdirect167248154
241024-MAY-08 10.19.51.985501 AMdirect168645175156
241124-MAY-07 11.22.10.548639 AMdirect169815760.5156
241229-MAR-06 10.22.09.509801 AMdirect170966816158
241329-MAR-08 01.34.04.525934 PMdirect101548552161
241429-MAR-07 02.22.40.536996 PMdirect102810794.6153
241529-MAR-06 01.34.50.545196 PMdirect1036310161
241629-MAR-07 04.41.20.945676 PMdirect1046384160
241720-MAR-07 05.49.10.974352 PMdirect10551926.6163
241820-MAR-04 04.18.21.862632 PMdirect10645546.6163
241920-MAR-07 07.03.32.764632 PMdirect107331574160
242013-MAR-07 08.59.43.666320 PMdirect108229750160
242112-MAR-07 09.53.54.562432 PMdirect109172836
242216-DEC-07 08.19.55.462332 PMdirect144211188.5153
242321-NOV-07 10.22.33.362632 AMdirect145310367.7160
242421-NOV-07 10.22.33.263332 AMdirect146413824153
242516-NOV-06 11.34.22.162552 PMdirect14751500.8163
242617-NOV-06 12.22.11.262552 AMdirect14867200
242710-NOV-07 01.34.22.362124 AMdirect14979055163
242810-NOV-07 02.41.34.463567 AMdirect116814685.8
242910-NOV-07 03.49.25.526321 AMdirect117950125154
243002-OCT-07 06.18.36.663332 AMdirect101829669.9159
243114-SEP-06 07.03.04.763452 AMdirect10215610.6163
243701-SEP-06 08.59.15.826132 AMdirect103413550163
243801-SEP-07 09.53.26.934626 AMdirect10405451154
243931-AUG-07 10.19.37.811132 AMdirect105122150.1159
244101-AUG-08 11.22.48.734526 AMdirect10652075.2160
244227-JUL-06 12.22.59.662632 PMdirect107952471.9154
244327-JUL-06 01.34.16.562632 PMdirect10803646154
244427-JUL-07 02.22.27.462632 PMdirect109177727.2155
244527-JUL-06 03.34.38.362632 PMdirect14485537.8158
244818-JUN-07 04.41.49.262632 PMdirect14551388158
244913-JUN-07 05.49.07.162632 PMdirect146686155
245011-APR-07 06.18.10.362632 PMdirect14731636159
245117-DEC-07 05.03.52.562632 PMdirect148710474.6154
245206-OCT-07 08.59.43.462632 PMdirect149512589159
245304-OCT-07 09.53.34.362632 PMdirect1160129153
245607-NOV-06 07.53.25.989889 PMdirect11703878.4163
245731-OCT-07 11.22.16.162632 PMdirect118521586.2159

Basic Usage
Sorting a result set is as easy as specifying the attribute you wish to sort by in the ORDER BY clause followed by “ASC” or “DESC.” These two keywords are short for ascending and descending, respectively. If the sorting method is omitted from the ORDER BY clause, then ascending order (ASC) is implied. As a word of caution, keep in mind making use of defaults in any programming language means you are operating under the assumption that the reader also knows the defaults. That said, you will notice I do make use of the default sort method in the examples on this page by not explicitly stating “ASC.”

Carrying on, let us see how easy it really is. The code below returns one row per job ID value and the average salary of the corresponding employees holding the specific job. The result set is sorted alphabetically in ascending (i.e., A-Z) order by the job ID values by using the ORDER BY clause followed by the pre-existing attribute, job_id.

SELECT
	hr.employees.job_id,
	AVG(hr.employees.salary) AS average_salary
FROM
	hr.employees
GROUP BY
	hr.employees.job_id
ORDER BY
	hr.employees.job_id;
job_idaverage_salary
AC_ACCOUNT8300
AC_MGR12008
AD_ASST4400
AD_PRES24000
AD_VP17000
FI_ACCOUNT7920
FI_MGR12008
HR_REP6500
IT_PROG5760
MK_MAN13000
MK_REP6000
PR_REP10000
PU_CLERK2780
PU_MAN11000
SA_MAN12200
SA_REP8350
SH_CLERK3215
ST_CLERK2785
ST_MAN7280

With an additional four characters, the result set can be sorted in descending order. See the code and corresponding output below.

SELECT
	hr.employees.job_id,
	AVG(hr.employees.salary) AS average_salary
FROM
	hr.employees
GROUP BY
	hr.employees.job_id
ORDER BY
	hr.employees.job_id DESC;
job_idaverage_salary
ST_MAN7280
ST_CLERK2785
SH_CLERK3215
SA_REP8350
SA_MAN12200
PU_MAN11000
PU_CLERK2780
PR_REP10000
MK_REP6000
MK_MAN13000
IT_PROG5760
HR_REP6500
FI_MGR12008
FI_ACCOUNT7920
AD_VP17000
AD_PRES24000
AD_ASST4400
AC_MGR12008
AC_ACCOUNT8300

In the previous examples, the result sets were sorted based on a single pre-existing attribute’s values. To sort a result set by multiple attributes, use the ORDER BY clause followed by a comma-separated list of attributes you wish to sort by. A concrete example can be found below. The code returns one row per manager ID and job ID combination along with the corresponding average employee salary. The result set is sorted by the manager ID values, ascending (i.e., least to greatest). Each group of grouped rows is subsequently sorted by the job ID values in descending order. For clarity, see the output following the code below.

SELECT
    hr.employees.manager_id,
	hr.employees.job_id,
	AVG(hr.employees.salary) AS average_salary
FROM
	hr.employees
GROUP BY
    hr.employees.manager_id,
	hr.employees.job_id
ORDER BY
    hr.employees.manager_id,
	hr.employees.job_id DESC;
manager_idjob_idaverage_salary
100ST_MAN7280
100SA_MAN12200
100PU_MAN11000
100MK_MAN13000
100AD_VP17000
101PR_REP10000
101HR_REP6500
101FI_MGR12008
101AD_ASST4400
101AC_MGR12008
102IT_PROG9000
103IT_PROG4950
108FI_ACCOUNT7920
114PU_CLERK2780
120ST_CLERK2625
120SH_CLERK2900
121ST_CLERK2675
121SH_CLERK3675
122ST_CLERK2700
122SH_CLERK3200
123ST_CLERK3000
123SH_CLERK3475
124ST_CLERK2925
124SH_CLERK2825
145SA_REP8500
146SA_REP8500
147SA_REP7766.666666666666666666666666666666666667
148SA_REP8650
149SA_REP8333.333333333333333333333333333333333333
201MK_REP6000
205AC_ACCOUNT8300
AD_PRES24000

In the output above, notice all grouped rows corresponding to the manager ID value of 100 are next to each other and the corresponding job ID values are in descending order (i.e., Z-A). This is no surprise given the code used to generate the output, but is useful to connect the dots on how multi-attribute sorting works using SQL.

Having walked through the ORDER BY clause’s basic usage through a handful of examples, let us now turn to sorting result sets by things other than pre-existing attributes.

ORDER BY Non-selected Attributes
The ORDER BY clause permits users to sort a result set based on values that can be derived using the result set but are not specified in the SELECT clause. For example, suppose you are tasked with generating a sales representative performance report. For each sales representative, the total number of orders placed by customers assisted by the corresponding sales representative and the total order total value are required. Additionally, the report needs to be sorted in descending order based on each sales representative’s average order total. The code below achieves this task by sorting based on the results of computing the average order total across each set of grouped rows (i.e., each sales representative’s orders).

SELECT
    oe.orders.sales_rep_id,
    COUNT(oe.orders.order_id) AS order_count,
    SUM(oe.orders.order_total) AS total_order_total
FROM
    oe.orders
WHERE
    oe.orders.sales_rep_id IS NOT NULL
GROUP BY
    oe.orders.sales_rep_id
ORDER BY
	AVG(oe.orders.order_total) DESC;
sales_rep_idorder_counttotal_order_total
16113661734.5
1565202617.6
1555134415.2
1535114215.7
1587156296.2
1597151167.2
15410171973.1
160688238.4
16312128249.5

ORDER BY Alias
Being able to sort a result set by an attribute’s alias can engender more readable code and save you keystrokes at the same time. In the example code below, the result set has been sorted in descending order based on the derived attribute, order_count, instead of the code used to produce the attribute and its values (i.e., COUNT(oe.orders.order_id)). While the benefit of this feature may not be significant here, the benefit is evident for derived attributes with more lengthy code required to produce them.

SELECT
    oe.orders.sales_rep_id,
    COUNT(oe.orders.order_id) AS order_count,
    SUM(oe.orders.order_total) AS total_order_total
FROM
    oe.orders
WHERE
    oe.orders.sales_rep_id IS NOT NULL
GROUP BY
    oe.orders.sales_rep_id
ORDER BY
	order_count DESC;
sales_rep_idorder_counttotal_order_total
16113661734.5
16312128249.5
15410171973.1
1597151167.2
1587156296.2
160688238.4
1535114215.7
1565202617.6
1555134415.2

Custom Sorting
There may be instances where it is required or desirable to sort values in ways that go beyond the standard methods of ascending order and descending order. For example, suppose you are designing a sign-up form for your new technology newsletter. To subscribe to the newsletter, customers must fill out the form containing various fields, including a field called “Country Name.” This field is meant to indicate where the customer resides. You believe the vast majority of your subscribers will be residents of the United States, so to make it easier for the majority to fill out the form, you wish to have the value, “United States of America,” appear as the first value in the field’s drop-down selector and all subsequent country name values to appear in alphabetical order. How can this be achieved using SQL? One method is to use a CASE expression to implement conditional logic. In the code below, a CASE expression is used to return 0 when the country ID is “US” and 1 for all other country ID values. Sorting the numeric values returned results in the value, United States of America, appearing in the first row. The second argument or attribute specified in the ORDER BY clause is country name. This is required to ensure all country name values following the first value (i.e., United Statues of America) are sorted in alphabetical order. If this second attribute was not included in the ORDER BY clause, then the remainder of country names would be in no particular order.

SELECT
	hr.countries.country_name AS "Country Name"
FROM
    hr.countries
ORDER BY
    CASE
    	WHEN hr.countries.country_id = 'US'
			THEN 0
		ELSE 1
	END,
	hr.countries.country_name;
Country Name
United States of America
Argentina
Australia
Belgium
Brazil
Canada
China
Denmark
Egypt
France
Germany
India
Israel
Italy
Japan
Kuwait
Malaysia
Mexico
Netherlands
Nigeria
Singapore
Switzerland
United Kingdom
Zambia
Zimbabwe

Handling Missing Values
Depending on the relational database management system (RDBMS) being used, NULL may appear at the beginning or at the end of a result set. For the examples on this page, Oracle Database 19c is used. By default, queries written using Oracle database will return NULLs first when the sorting specified is ascending and last when descending order is specified. It may be easier to think of it this way: For columns of numeric data type, NULL is treated as the largest value and for columns of character data type, NULL is last in terms of alphabetical order. An example for each scenario follows. For clarity, the code and corresponding output is provided.

-- Number of employees corresponding to each manager ID value.
SELECT
	hr.employees.manager_id,
    COUNT(hr.employees.employee_id) AS employee_count
FROM
	hr.employees
GROUP BY
	hr.employees.manager_id
ORDER BY
	hr.employees.manager_id;
manager_idemployee_count
10014
1015
1021
1034
1085
1145
1208
1218
1228
1238
1248
1456
1466
1476
1486
1496
2011
2051
1

Notice in the example above, the row corresponding to the single employee not reporting to a manager appears last. In the example below, the number of employees not belonging to a department appears first because the sorting specified is descending order.

-- Number of employees corresponding to each department name value.
SELECT
	hr.departments.department_name,
	COUNT(hr.employees.employee_id) AS employee_count
FROM
	hr.employees
    LEFT JOIN
    hr.departments
    	ON hr.employees.department_id = hr.departments.department_id
GROUP BY
	hr.departments.department_name
ORDER BY
	hr.departments.department_name DESC;
department_nameemployee_count
1
Shipping45
Sales34
Purchasing6
Public Relations1
Marketing2
IT5
Human Resources1
Finance6
Executive3
Administration1
Accounting2

Knowledge Check
If you’d like to confirm your understanding on the ORDER BY clause and other fundamental concepts, consider solving a handful of my practice problems here.