Select Star SQL

Lange staart

Lange staarten verwijzen naar kleine aantallen monsters die een groot aantal keren voorkomen. Wanneer we deze uitzetten, vormen ze een kleine strook ver rechts van het massamiddelpunt die eruitziet als een staart. Ze duiden op de aanwezigheid van uitschieters waarvan het ongewone gedrag interessant voor ons kan zijn. In de context van Texas executies verwijst de lange staart naar een klein aantal counties waarvan bekend is dat ze een groot aantal executies uitvoeren.

Laten we het percentage executies van elke provincie vinden, zodat we de executies in de staart eruit kunnen pikken.

Zoals steeds duidelijker zal worden, vertelt de vorm van de tabellen ons veel over de bewerkingen die we moeten uitvoeren. (Dit is analoog aan de dimensionale analyse in de natuurkunde.) In dit geval kunnen we vaststellen dat de methoden die we tot nu toe behandeld hebben, ontoereikend zijn: Het Beazley hoofdstuk ging over individuele rijen gegevens, maar het is duidelijk dat we moeten aggregeren om gegevens op county-niveau te vinden. Het Claims of Innocence hoofdstuk leerde ons aggregatie, maar die functies zouden uiteindelijk de dataset aggregeren tot één rij, terwijl we eigenlijk één rij per county willen.


Het GROUP BY blok

Hier komt het GROUP BY blok om de hoek kijken. Hiermee kunnen we de dataset opsplitsen en aggregatiefuncties toepassen binnen elke groep, wat resulteert in één rij per groep. De meest eenvoudige vorm is GROUP BY <kolom>, <kolom>, ... en komt na het blok WHERE.

Als je je A Strange Query herinnert, gaan er alarmbellen af in je hoofd. Hadden we net niet geleerd om geaggregeerde en niet-geaggregeerde kolommen niet te mixen? Het verschil hier is dat groeperingskolommen de enige kolommen zijn die niet-geaggregeerd mogen zijn. Immers, alle rijen in die groep moeten dezelfde waarden hebben op die kolommen, zodat er geen dubbelzinnigheid is in de waarde die moet worden geretourneerd.

Je hebt misschien ook ons gebruik van AS opgemerkt. Dit noemen we “aliasing”. In het SELECT-blok geeft <expression> AS <alias> een alias waarnaar later in de query kan worden verwezen. Dit bespaart ons het herschrijven van lange expressies en stelt ons in staat om het doel van de expressie te verduidelijken.


Het blok HAVING

De volgende oefening illustreert dat filteren via het WHERE blok gebeurt vóór groeperen en aggregeren. Dit wordt weerspiegeld in de volgorde van de syntax aangezien het WHERE blok altijd voorafgaat aan het GROUP BY blok.

Dit is allemaal goed en wel, maar wat gebeurt er als we willen filteren op het resultaat van het groeperen en aggregeren? We kunnen toch niet vooruit springen in de toekomst en daar informatie vandaan halen. Om dit probleem op te lossen, gebruiken we HAVING.


Praktijk

Deze quiz is ontworpen om je begrip uit te dagen. Lees de uitleg, zelfs als je alles juist hebt.


Geneste Queries

Nu vraag je je misschien af: zouden we niet klaar zijn als we gewoon zoiets als dit konden uitvoeren?

SELECT
  county,
  PERCENT_COUNT(*)
FROM executions
GROUP BY county

Percentages zijn zo’n veelgebruikte metriek—zou zo’n functie niet moeten bestaan? Helaas niet, en misschien met een goede reden: Zo’n functie zou moeten aggregeren, zowel binnen de groepen (om de teller te krijgen) als in de hele dataset (om de noemer te krijgen). Maar elke query heeft of een GROUP BY blok of niet. Dus wat we echt nodig hebben zijn twee aparte queries, een die aggregeert met een GROUP BY en een andere die aggregeert zonder. We kunnen ze dan combineren met een techniek die “nesting” heet.

Hier is een voorbeeld van hoe nesten werkt. De haakjes zijn belangrijk om de grens aan te geven tussen de binnenste query en de buitenste:

Nogmaals, nesting is hier nodig omdat in de WHERE-clausule, wanneer de computer een rij inspecteert om te beslissen of de laatste uitspraak de juiste lengte heeft, hij niet naar buiten kan kijken om de maximale lengte voor de hele dataset te achterhalen. We moeten de maximale lengte afzonderlijk vinden en deze in de clausule invoeren. Laten we nu hetzelfde concept toepassen om het percentage executies uit elke provincie te vinden.

Ik heb stilletjes een ORDER BY blok toegevoegd. Het formaat is ORDER BY <kolom>, <kolom>, ... en het kan worden aangepast door DESC toe te voegen als je de standaard oplopende volgorde niet wilt.


Provincie Harris

Is het verrassend dat Harris (de stad Houston), Dallas, Bexar en Tarrant goed zijn voor ongeveer 50% van alle executies in Texas? Misschien wel, vooral als we uitgaan van de veronderstelling dat executies gelijk verdeeld moeten zijn over de counties. Maar een betere eerste benadering is dat executies worden verdeeld in lijn met de bevolkingsverdeling. De [2010 Texas Census] (https://www.tsl.texas.gov/ref/abouttx/popcnty12010.html) laat zien dat de 4 county’s een bevolking hadden van 10,0 miljoen, wat 40,0% is van de bevolking van Texas (25,1 miljoen). Dit maakt de bevinding iets minder verrassend.

Maar door deze staart verder uit te splitsen, realiseren we ons dat de county Harris verantwoordelijk is voor het grootste deel van de delta. Het heeft slechts 16,4% van de bevolking, maar 23,1% van de executies. Dat is bijna 50% meer dan het zou moeten hebben.

Talloze studies hebben onderzocht waarom Harris County zo productief is en er zijn verschillende factoren naar voren gebracht:


Samenvatting

In dit gedeelte hebben we geleerd om te aggregeren over groepen en om nesting te gebruiken om de uitvoer van een binnenquery te gebruiken in een buitenquery. Deze technieken hebben het zeer praktische voordeel dat ze ons in staat stellen percentages te berekenen.

MapReduce

Een interessante toevoeging is dat we eigenlijk net hebben geleerd om MapReduce te doen in SQL. MapReduce is een bekend programmeerparadigma dat berekeningen ziet als uitgevoerd in een "map" en "reduce" stap. Je kunt hier meer leren over MapReduce.

Het Beazley hoofdstuk ging helemaal over mapping omdat het ons liet zien hoe we verschillende operaties konden mappen naar alle rijen. Bijvoorbeeld, SELECT LENGTH(last_statement) FROM executions mapt de lengte functie uit naar alle rijen. Dit hoofdstuk liet ons zien hoe we verschillende groepen gegevens kunnen verkleinen met aggregatiefuncties; en het vorige Claims of Innocence hoofdstuk was slechts een speciaal geval waarin de hele tabel één groep is.

In het volgende hoofdstuk leren we over JOIN's waarmee we met meerdere tabellen kunnen werken.