MySQL (24) - Seskupujeme záznamy
Mít spoustu dat je hezká věc, ale občas bychom spíše potřebovali udělat z nich nějaký "výcuc". O tom je dnešní díl seriálu o MySQL.
10.6.2005 06:00 |
Petr Zajíc
| Články autora
| přečteno 52063×
Již víme, že tabulky se v dotazech dají spojovat. Dosud jsme ale
pracovali způsobem, při němž se vždy ve výsledku dotazu zobrazily
všechny (nebo vybrané) řádky z jedné či více tabulek. To může pro
základní práci s databází sice stačit, ale většinou je to málo. Pojďme
se dnes začít zabývat seskupováním záznamů.
Seskupování záznamů
Abychom byli od začátku přesní - seskupování záznamů je něco jiného
než spojování tabulek. Při spojování tabulek totiž pracujete se dvěma
nebo více tabulkami s cílem najít záznamy, které spolu vzájemně
souvisejí. (Exaktně řečeno lze spojit tabulku i samu se sebou, je to
však speciální případ a probereme to později samostatně). Seskupování
naproti tomu je proces, který probíhá s cílem zjistit něco o skupině
nějak souvisejících záznamů. "Skupina nějak souvisejících záznamů"
přitom může být docela dobře v jediné tabulce. V praxi bychom mohli
najít mnoho případů seskupování:
- Aplikace vyhodnocující přístup k internetovým stránkám bude chtít
vědět, kolik přístupů byl zaznamenáno v jednotlivých dnes provozu webu
- Aplikace pro fakturaci bude chtít zjistit, jaká je celková cena
bez DPH, DPH a cena s daní po sečtení všech položek faktury
- Aplikace pro statistiku v meteorologii bude chtít vědět, jaká
byla průměrná teplota pro dnešní den v několika předcházejících
desetiletích
- Krásný příklad - budete chtít zjistit z databáze zaměstnanců, kdo
má vyšší plat, než je průměr ve vaší firmě.
Představme si například následující tabulku, která by mohla
vzniknout jako záznam z nějakého toho logu návštěvnosti webu. Ukládá
datum návštěvy, operační systém uživatele, jeho prohlížeč, stránku,
kterou navštívil a čas, který tím strávil:
create table logtable
(datum datetime, system varchar(20),
prohlizec varchar(20), stranka varchar(20), doba_prohlizeni int);
insert into logtable (datum, system, prohlizec, stranka, doba_prohlizeni )
values ('20050609132500','windows','ie6','index.php',5);
insert into logtable (datum, system, prohlizec, stranka , doba_prohlizeni )
values ('20050609132510','windows','ie6','data.php',7);
insert into logtable (datum, system, prohlizec, stranka , doba_prohlizeni )
values ('20050609132740','linux','firefox','index.php',9);
insert into logtable (datum, system, prohlizec, stranka , doba_prohlizeni )
values ('20050609132810','linux','firefox','formular.php',35);
insert into logtable (datum, system, prohlizec, stranka , doba_prohlizeni )
values ('20050609132810','unix','opera','index.php',6);
insert into logtable (datum, system, prohlizec, stranka , doba_prohlizeni )
values ('20050609132850','linux','firefox','data.php',15);
insert into logtable (datum, system, prohlizec, stranka , doba_prohlizeni )
values ('20050609132930','unix','opera','data.php',18);
insert into logtable (datum, system, prohlizec, stranka , doba_prohlizeni )
values ('20050610082500','linux','opera','index.php',44);
insert into logtable (datum, system, prohlizec, stranka , doba_prohlizeni )
values ('20050610091106','unix','firefox','formular.php',20);
Pozn.: Omlouvám se za délku, ale
pokud si to budete chtít vyzkoušet, nějaká ta data je při testech
seskupování záznamů třeba mít po ruce.
Seskupování záznamů probíhá tak, že se za příkaz SELECT uvede
klauzule GROUP BY [název pole,[název pole...]], která přikáže serveru
data před jejich vrácením seskupit. V nejjednodušším případě to může
vypadat nějak takto:
select * from logtable
group by system;
Pokud si to zkoušíte, asi nejste z výsledku příliš nadšeni. MySQL
totiž vybere z celé tabulky vždy první záznam o systému, který tu ještě
nebyl, a ten vrátí. Ve výsledku tedy bude jeden řádek s linuxem, jeden
s unixem a jeden s windows. Ze seskupování se ale dá vyzískat mnohem
víc, když se použijí
Agregační funkce
Agregační funkce umožňují "něco" vypočítat z řádků, které se právě
seskupují. Přestože těchto funkcí existuje celá řada, v praxi pro
většinu běžných úloh typicky stačí znát pouze dvě z nich:
- Agregační funkce COUNT, která zjistí počet právě seskupovaných
řádků
- Agregační funkce SUM, která zjistí součet položek v právě
seskupovaných řádcích
Obě teď můžeme předvést na příkladu. Pomocí agregační funkce COUNT
můžeme
z protokolu například zjistit, kolik přístupů zaznamenala ta která
stránka:
select stranka, count(*)
from logtable group by stranka;
A pomocí SUM můžeme třeba vypátrat, kolik času na jednotlivých
stránkách naši návštěvníci tráví:
select stranka,
sum(doba_prohlizeni) from logtable group by stranka;
K agregačním funkcím se váže celá řada postřehů a zásad, které je
dobře znát. Tak například za klauzulí GROUP BY nemusí být uveden jeden
sloupec, ale může jich být hned několik. Není to takový nesmysl, jak by
se mohlo na první pohled zdát. Můžeme třebas náš příkad s funkcí COUNT
chtít rozšířit tak, aby vracel počet shlédnutí stránky podle stránky a
prohlížeče, jímž se na tuto stránku přistupovalo. V tom případě bude
vrácen počet přístupů pro každou
kombinaci stránky a prohlížeče:
select stranka,
prohlizec, count(*) from logtable group by stranka, prohlizec;
Dále, nic nám nebrání sestavit dotaz, v němž bude jak klauzule
WHERE, tak i GROUP BY (ve skutečnosti je to celkem častý případ).
Jestliže nás bude zajímat jen chování uživatelů Firexofu, můžeme
předchozí příklad přepsat použitím:
select stranka,
prohlizec, count(*) from logtable where prohlizec = 'firefox' group by
stranka, prohlizec;
Konečně, jednou seskupené řádky lze řadit. Uvědomme si, že řazení
probíhá až PO seskupení záznamů. To má dva praktické důsledky:
- Klauzule ORDER BY je v příkazu SELECT vždy až na posledním místě.
Logicky to odpovídá pořadí, v němž dotaz bude zpracováván. Takže, z nám
známých rozšíření příkazu SQL je zatím pořadí toto: SELECT ... FROM ...
JOIN ... WHERE ... GROUP BY ... ORDER BY. Začátečníkovi to sice může
připadat poněkud náročné na zapamatování, ale je to intuitivní.
- Jelikož probíhá řazení až nakonec, můžeme řadit podle výsledku
agregační funkce! Nebyl by tedy problém seřadit například stránky
sestupně podle doby, kterou na nich uživatelé tráví. Ovšem pozor,
sytaxe, která vás v této souvislosti asi napadne nejdřív, nefunguje:
select stranka,
sum(doba_prohlizeni) from logtable group by stranka order by
sum(doba_prohlizeni) desc;
Důvod je prostý - MySQL nesmí mít v klauzuli ORDER BY výraz. Řešení
jsou dvě, buď se dá použít číslo řazeného sloupce, nebo si výraz SUM
(doba_prohlizeni) nazvat aliasem. Oba dotazy níže již projdou a dělají
totéž:
select stranka,
sum(doba_prohlizeni) as doba from logtable group by stranka order by
doba desc;
select stranka, sum(doba_prohlizeni) from logtable group by stranka
order by 2 desc;
V příštím díle se můžete těšit na další informace ohledně
seskupování záznamů.
Verze pro tisk
|
Příspívat do diskuze mohou pouze registrovaní uživatelé.
|
|

Vyhledávání software

Vyhledávání článků
28.11.2018 23:56 /František Kučera Prosincový sraz spolku OpenAlt se koná ve středu 5.12.2018 od 16:00 na adrese Zikova 1903/4, Praha 6. Tentokrát navštívíme organizaci CESNET. Na programu jsou dvě přednášky: Distribuované úložiště Ceph (Michal Strnad) a Plně šifrovaný disk na moderním systému (Ondřej Caletka). Následně se přesuneme do některé z nedalekých restaurací, kde budeme pokračovat v diskusi.
Komentářů: 1
12.11.2018 21:28 /Redakce Linuxsoft.cz 22. listopadu 2018 se koná v Praze na Karlově náměstí již pátý ročník konference s tématem Datová centra pro business, která nabídne odpovědi na aktuální a často řešené otázky: Jaké jsou aktuální trendy v oblasti datových center a jak je optimálně využít pro vlastní prospěch? Jak si zajistit odpovídající služby datových center? Podle jakých kritérií vybírat dodavatele služeb? Jak volit vhodné součásti infrastruktury při budování či rozšiřování vlastního datového centra? Jak efektivně datové centrum spravovat? Jak co nejlépe eliminovat možná rizika? apod. Příznivci LinuxSoftu mohou při registraci uplatnit kód LIN350, který jim přinese zvýhodněné vstupné s 50% slevou.
Přidat komentář
6.11.2018 2:04 /František Kučera Říjnový pražský sraz spolku OpenAlt se koná v listopadu – již tento čtvrtek – 8. 11. 2018 od 18:00 v Radegastovně Perón (Stroupežnického 20, Praha 5). Tentokrát bez oficiální přednášky, ale zato s dobrým jídlem a pivem – volná diskuse na téma umění a technologie, IoT, CNC, svobodný software, hardware a další hračky.
Přidat komentář
4.10.2018 21:30 /Ondřej Čečák LinuxDays 2018 již tento víkend, registrace je otevřená.
Přidat komentář
18.9.2018 23:30 /František Kučera Zářijový pražský sraz spolku OpenAlt se koná již tento čtvrtek – 20. 9. 2018 od 18:00 v Radegastovně Perón (Stroupežnického 20, Praha 5). Tentokrát bez oficiální přednášky, ale zato s dobrým jídlem a pivem – volná diskuse na téma IoT, CNC, svobodný software, hardware a další hračky.
Přidat komentář
9.9.2018 14:15 /Redakce Linuxsoft.cz 20.9.2018 proběhne v pražském Kongresovém centru Vavruška konference Mobilní řešení pro business.
Návštěvníci si vyslechnou mimo jiné přednášky na témata: Nejdůležitější aktuální trendy v oblasti mobilních technologií, správa a zabezpečení mobilních zařízení ve firmách, jak mobilně přistupovat k informačnímu systému firmy, kdy se vyplatí používat odolná mobilní zařízení nebo jak zabezpečit mobilní komunikaci.
Přidat komentář
12.8.2018 16:58 /František Kučera Srpnový pražský sraz spolku OpenAlt se koná ve čtvrtek – 16. 8. 2018 od 19:00 v Kavárně Ideál (Sázavská 30, Praha), kde máme rezervovaný salonek. Tentokrát jsou tématem srazu databáze prezentaci svého projektu si pro nás připravil Standa Dzik. Dále bude prostor, abychom probrali nápady na využití IoT a sítě The Things Network, případně další témata.
Přidat komentář
16.7.2018 1:05 /František Kučera Červencový pražský sraz spolku OpenAlt se koná již tento čtvrtek – 19. 7. 2018 od 18:00 v Kavárně Ideál (Sázavská 30, Praha), kde máme rezervovaný salonek. Tentokrát bude přednáška na téma: automatizační nástroj Ansible, kterou si připravil Martin Vicián.
Přidat komentář
Více ...
Přidat zprávičku
 Poslední diskuze
31.7.2023 14:13 /
Linda Graham iPhone Services
30.11.2022 9:32 /
Kyle McDermott Hosting download unavailable
13.12.2018 10:57 /
Jan Mareš Re: zavináč
2.12.2018 23:56 /
František Kučera Sraz
5.10.2018 17:12 /
Jakub Kuljovsky Re: Jaký kurz a software by jste doporučili pro začínajcího kodéra?
Více ...
|