Lekce 08 · 18 min čtení
Multi-head + poziční kódování
Víc hlav pozornosti naráz a jak modelu vůbec říct, v jakém pořadí slova jdou.
Úvod
V minulé lekci jsme postavili jednu hlavu pozornosti. Naučila se pěkný vztah: sloveso si najde svůj podmět a předmět. Jenže ve větě běží vztahů víc najednou. Kdo s kým, co kde, co bylo dřív. Jedna hlava to všechno naráz neuhlídá, protože si musí vybrat jeden vzorec dotazů a klíčů.
Řešení je otravně jednoduché: pusť na větu víc hlav zároveň, každou s vlastníma očima. A pak vyřešíme jeden tichý problém, kterého sis možná všiml už minule: attention vůbec netuší, v jakém pořadí slova jdou.

Více pohledů na tutéž situaci. A pořadí v řadě se nesmí poplést.
Víc hlav pozornosti
Multi-head attention není nic jiného než několik attention z minulé lekce běžících vedle sebe. Každá hlava má svoje vlastní matice pro Query, Key a Value, takže si každá počítá svoje skóre a dívá se jinam. Jedna se naučí hlídat vazby slovesa, jiná místo, další třeba kdo je v ději.
Tady jsou tři hlavy nad naší větou. Vyber slovo a koukni, jak se každá dívá jinam:
MultiHeadAttention · víc úhlů pohledu naráz
Vyber slovo a koukni, jak se na něj dívá každá hlava jinak.
hlava 1 · vazby slovesa
kdo co dělá s čím
- pan
- švejk
- vypil
- pivo
- v
- hospodě
hlava 2 · místo
kde se to odehrává
- pan
- švejk
- vypil
- pivo
- v
- hospodě
hlava 3 · postavy
kdo je ve hře
- pan
- švejk
- vypil
- pivo
- v
- hospodě
Tři hlavy, tři pohledy na slovo vypil. Jejich výstupy se pak slepí za sebe a prožene se jedna vrstva navrch.
Vyber třeba vypil. První hlava si najde, kdo pil a co (pan, švejk, pivo).
Druhá hlava řeší, kde se to dělo (hospodě). Třetí sleduje postavy. Tři pohledy
na to samé slovo, každý užitečný pro něco jiného. Tohle žádná jednotlivá hlava
nedokáže, musela by se rozhodnout pro jeden vzorec.
Jak to do sebe zapadá
Kdyby každá hlava pracovala v plné velikosti embeddingu, bylo by to draho. Trik je, že se rozměr rozdělí mezi hlavy. Když má embedding velikost 512 a máš 8 hlav, každá hlava pracuje jen v rozměru 64. Spočítají se paralelně, jejich výstupy se slepí za sebe zpátky na 512 a prožene se jedna závěrečná vrstva.
Takže víc pohledů přijde skoro zadarmo. Místo jedné velké hlavy máš osm menších, každou specializovanou. Celkový počet čísel zůstane zhruba stejný.
Tichý problém: attention neví, kde co stojí
Teď ta zákeřnost. Vrať se k vzorci attention z minulé lekce. Je to vážený součet
přes všechna slova. A součtu je jedno pořadí. a + b je to samé jako b + a.
To znamená, že čistá attention vůbec nerozlišuje, v jakém pořadí slova přišla. Věta „pes kousl muže" a „muž kousl psa" obsahují stejná slova, takže by z holé attention vypadlo to samé. A to je očividně špatně. Pořadí ve větě nese půlku významu.
Poziční kódování
Oprava je elegantní: ke každému slovu přičteme vektor, který kóduje jeho pozici. Slovo na první pozici dostane jiný „otisk" než to samé slovo na páté. Model tak má pořadí přímo ve vstupu, ještě než attention začne.
Klasický recept používá siny a kosiny o různých frekvencích. Každá pozice tím dostane unikátní vzorec čísel:
Nemusíš ten vzorec milovat, stačí pochopit záměr: vyrobit pro každou pozici rozpoznatelný otisk, který se přičte k embeddingu. Pojďme si ty otisky vypsat:
Každý řádek je jiný, takže model dokáže první slovo odlišit od pátého. Mimochodem, moderní modely tenhle konkrétní sinusový recept často nahrazují pozicemi, které se model rovnou naučí, ale myšlenka zůstává: bez informace o pozici by si slova ve větě byla na nerozeznání.
V kódu
Teď celá multi-head attention v numpy. Tři hlavy, každá si promítne vstup do svého menšího rozměru, spočítá attention, a výstupy se slepí. Klikni Run.
Všimni si těch rozměrů. Tři hlavy po 4 se slepí zpátky na 12, takže vstup i výstup mají stejný tvar. To je důležité, protože tyhle bloky se budou v transformeru stohovat na sebe a každý musí dostat to, co předchozí vydal.
Cvičení
Cvičení · lekce8-cv1
Model má embedding velikosti 512 a 8 hlav pozornosti. V jakém rozměru
pracuje jedna hlava?
Cvičení · lekce8-cv2
Těch 8 hlav po 64 se slepí za sebe. Jakou délku má vektor po slepení?
Cvičení · lekce8-cv3
Pozná čistá attention bez pozičního kódování rozdíl mezi větami „pes kousl muže" a „muž kousl psa"? (1 = ano, 0 = ne.)
Cvičení · lekce8-cv4
V playgroundu nahoře proklikej slova a hlavy. Najdi hlavu, která se ti zdá nejužitečnější, a napiš, jaký vztah podle tebe sleduje.
Shrnutí
- Multi-head attention pustí na větu víc hlav naráz, každou s vlastními Q/K/V. Každá se může naučit jiný typ vztahu.
- Rozměr se mezi hlavy rozdělí, hlavy běží paralelně a jejich výstupy se slepí zpátky: .
- Čistá attention je slepá vůči pořadí slov, protože je to jen vážený součet.
- Poziční kódování přičte ke každému slovu otisk jeho pozice, takže model ví, co stálo kde.
- Vstup a výstup bloku mají stejný tvar, což umožní bloky stohovat na sebe.
Co bude příště
Máme všechny součástky transformeru: embeddingy, poziční kódování, multi-head attention. Zbývá je poskládat do jednoho bloku a ukázat dvě lepidla, která to drží pohromadě i v hloubce: reziduální spojení a normalizaci.
V Lekci 9 (Transformer blok) složíme jeden kompletní blok, ze kterého se stohováním stane celý transformer. Pak už zbývá jen finální projekt.