I anledningen af det nye år har jeg fundet en rigtig godbid til alle os, der elsker SQL. I DB2 10 blev de såkaldte OLAP functions udvidet kraftigt med mulighed for summer og totaler og rullende gennemsnit og alt muligt andet i samme stil. Jeg blev introduceret for disse funktioner allerede da DB2 10 blev annonceret, men jeg tænkte ved mig selv, at det får jeg da ikke lige brug for.
En af de ting, der altid irriterer mig, når jeg skal lave en group by med noget COUNT(*) er, at jeg ikke i samme hug kan få en total af alle mine COUNT's. Så jeg tænkte, at det må de nye OLAP functions kunne hjælpe mig med. Det viste sig i den grad at være tilfældet, men først skulle jeg lige finde ud af, at jeg ikke kunne anvende GROUP BY til at opnå det ønskede resultat. Det var lidt underligt, men det skyldes, at OLAP functions opererer på resultatet efter GROUP BY. Når først du er nået til denne erkendelse, så kan du skrue de vildeste SQL statements sammen. Jeg vil illustrere det med et mindre vildt statement. Det vil fungere på din installation, men sandsynligvis ikke give præcis samme resultat:
Det første iøjnefaldende er brugen af distinct, som i princippet erstatter din GROUP BY. Det andet iøjnefaldende er udtrykkene efter i dette tilfælde SUM-funktionen. OVER angiver, at der skal udføres en OLAP function på kolonneresultatet. I parentesen angives OLAP funktionen. PARTITION BY svarer til GROUP BY, mens ORDER BY arbejder på det samlede resultat. SUM(1) erstatter COUNT(*), og sørger for, at hver række før DISTINCT udføres tæller netop een gang. Læg mærke til, at kolonnen eller kolonnerne efter PARTITION BY eller ORDER BY ikke behøver at være de samme for hver resultat-kolonne, og det er her, at det kan blive helt vildt. Jeg har holdt mig til samme kolonne alle steder, også i den afsluttende ORDER BY for at sikre, at resultatet ligner resultatet efter en GROUP BY. Og resultatet kan se således ud:
Kolonnen COLCOUNT indeholder antallet af kolonner på alle SYSIBM-tabellerne i den pågældende database. Kolonnen COLTOTAL indeholder en løbende sum af antallet af kolonner, så den sidste række indeholder det samlede antal kolonner på alle SYSIBM-tabeller. TABLECOUNT indeholder antallet af SYSIBM-tabeller i den pågældende database, mens TABLETOTAL er en løbende sum på antallet, så den sidste række indeholder det totale antal SYSIBM-tabeller. Uden brug af OLAP functions havde jeg anvendt fire SQL statements til at opnå samme resultat. Wow, det kalder jeg tæt på skræmmende godt.
Hvis du undrer dig, over, hvorfor jeg ikke har et link til SQL reference beskrivelsen af OLAP functions, så skyldes det, at IBM ikke længere udgiver deres DB2 manualer i Book Manager format på internettet. I stedet har IBM først indført noget de kaldte Information Center, som var sindsygt ringe, og nu har de erkendt dette og indført noget, de kalder Knowledge Center, som er mindst lige så ringe.