Imparare dal suono senza etichette#
Chi trascrive migliaia di ore di audio? Qualcuno deve farlo: per insegnare a una macchina a riconoscere il parlato servono coppie (audio, testo), e quel testo lo scrive una persona, ascoltando e battendo a tastiera. È lento, costa, e per molte lingue del mondo semplicemente non esiste. Eppure di audio non etichettato ce n’è a valanga: podcast, audiolibri, video, archivi radiofonici, registrazioni di ogni tipo; montagne di suono che nessuno ha mai trascritto.
C’è uno spreco evidente in tutto questo, e una domanda che se ne ricava: e se la macchina imparasse la struttura del suono da sola, ascoltando quelle montagne di audio grezzo, e usassimo poi ciò che ha imparato per i compiti veri (riconoscere il parlato, classificare suoni, generare musica) con poche etichette? È l’idea dell’apprendimento auto-supervisionato (self-supervised).
Una parola regge tutto quello che segue, e conviene fissarla subito: rappresentazione. È il gruppetto di numeri con cui un modello si tiene in mente un pezzetto di suono: qualche centinaio di numeri ogni venti millesimi di secondo, cioè cinquanta gruppetti per ogni secondo di audio, che nessuno ha scritto a mano e che nessuno saprebbe leggere uno per uno.
Quando è che una rappresentazione è migliore di un’altra? Immagina di appendere ogni pezzetto di suono in un punto di una stanza enorme, scegliendo il punto in base ai suoi numeri. Una buona rappresentazione è quella che appende vicini i pezzetti che si somigliano davvero e lontani quelli diversi: tutte le «s» in un angolo, tutte le «a» in un altro, i colpi di tamburo da tutt’altra parte. Se la stanza è ordinata così, qualunque domanda arrivi dopo («che vocale è?», «che strumento sta suonando?») si risponde tracciando una riga fra due zone, e diventa facile. Anche lo spettrogramma di Dal suono alle feature era una rappresentazione, ma l’avevamo disegnata noi; qui il modello se la costruisce da sé.
Nel testo scritto lo stesso passaggio è già avvenuto, ed è il precedente da cui questa storia nasce. Prima ogni parola aveva il suo gruppetto di numeri fisso, identico in qualunque frase (sono i word embedding, word2vec e simili, visti in Rappresentare il testo); poi si è passati a numeri che cambiano con la frase intorno, così che la «pesca» del contadino e la «pesca» del pescatore smettano di essere la stessa cosa, ed è il salto dei grandi modelli pre-addestrati come BERT. Nell’audio lo stesso passaggio è avvenuto più tardi, ed è la storia che segue.
Diamo per acquisite le rappresentazioni di base del suono (campionamento, spettrogramma, scala mel, MFCC) che abbiamo costruito nella sezione Dal suono alle feature: qui non ripartiamo dall’onda di pressione, ma da come un modello impara da sé una rappresentazione migliore.
Il problema delle etichette#
Il problema è di conti, e si fa in fretta. Un’ora di parlato richiede a un trascrittore diverse ore di lavoro; le ore di parlato che servirebbero sono migliaia; e per una lingua parlata da poche persone quel lavoro non lo ha fatto mai nessuno e non lo farà. Le etichette, cioè le risposte giuste scritte da un umano accanto a ogni esempio, sono la cosa più cara che c’è.
La via d’uscita è spezzare l’apprendimento in due tempi. Prima una lunga fase di studio su una massa enorme di audio senza risposte, per imparare come è fatto il suono in generale; poi una breve rifinitura sul compito vero, con le poche etichette che si hanno. Sono il pre-addestramento e la rifinitura, cioè il pretraining e il fine-tuning che la visione artificiale chiama insieme transfer learning, e il paradigma è lo stesso dei modelli linguistici del capitolo sui Transformer. Il lavoro pesante si fa una volta sola, e ogni compito successivo riparte da lì.
Un bambino impara i suoni della sua lingua molto prima che qualcuno gli insegni a scrivere. A furia di ascoltare, si accorge da solo che certi suoni tornano, che alcune combinazioni sono possibili e altre no, che «pa» e «ba» sono cose diverse, e tutto questo senza che nessuno gli abbia mai mostrato come si scrivono. Quando poi va a scuola e impara l’alfabeto, parte avvantaggiato: l’orecchio ha già fatto metà del lavoro.
L’auto-supervisione fa esattamente questo con una macchina. Prima le facciamo ascoltare montagne di audio senza dirle mai «qui c’è scritto così»: impara da sola la struttura del suono. Solo dopo le mostriamo poche ore di audio trascritto, per collegare quella struttura alle parole. Il guadagno è concreto: le etichette costose servono in quantità molto minore, perché il grosso (com’è fatto il parlato) è già stato imparato gratis.
Formalmente disponiamo di un grande insieme di audio non etichettato \(\mathcal{D}_U\) (decine di migliaia di ore) e di un piccolo insieme etichettato \(\mathcal{D}_L = \{(\mathbf{x}^{(i)}, \mathbf{y}^{(i)})\}\), con \(|\mathcal{D}_L| \ll |\mathcal{D}_U|\) (il simbolo \(\mathcal{L}\) resta riservato alle funzioni di perdita). Il pretraining ottimizza su \(\mathcal{D}_U\) un obiettivo che non richiede \(\mathbf{y}\), un pretesto (pretext task) costruito dai dati stessi, per apprendere un encoder \(F_\theta\) che mappa la forma d’onda in rappresentazioni contestuali (maiuscolo perché più avanti \(f\) sarà il solo stadio convoluzionale, e qui si intende tutta la catena). Il fine-tuning aggiunge sopra \(F_\theta\) una testa leggera (per il riconoscimento vocale, tipicamente uno strato con perdita CTC, che la sezione sui modelli di riconoscimento costruisce da capo) e la addestra su \(\mathcal{D}_L\): in tutti e due i lavori lo stadio convoluzionale resta congelato e il Transformer si sblocca dopo un certo numero di passi.
Il punto empirico che rende il tutto interessante è la curva di efficienza dei dati: partendo da un encoder pre-addestrato, il WER a valle crolla con pochissime etichette, là dove un modello addestrato da zero avrebbe bisogno di ordini di grandezza in più. È la stessa promessa del transfer learning nella visione, trasferita al dominio del suono.
wav2vec 2.0: mascherare il suono#
Il modello che rende questa idea pienamente convincente per il parlato è wav2vec 2.0, di Alexei Baevski e colleghi a Facebook AI (il laboratorio che oggi si chiama Meta AI) nel 2020 [BZMA20]. La ricetta ricalca il «gioco della parola coperta» che nel testo ha reso grande BERT (il cloze test, riempire il buco in una frase) ma applicato a pezzetti di suono invece che a parole (Fig. 22.5).
Fig. 22.5 Il gioco della parte coperta: sotto la mascherina c’è una delle unità dell’alfabeto sonoro, e il modello deve riconoscere quale, fra la giusta e i distrattori.#
Torna il gioco della frase da completare. Se copro una parola in «Il gatto nero salta sul ___», tu indovini «muro» perché conosci come funziona la lingua. wav2vec 2.0 gioca lo stesso gioco con il suono: prende un pezzo di audio, ne copre dei pezzetti, e chiede al modello di indovinare che cosa c’era sotto.
Ma con un aiuto, perché inventare il suono esatto da zero sarebbe un’impresa disperata. Il modello ha davanti un elenco di pezzetti-tipo, una specie di alfabeto sonoro: ognuno si chiama unità. Le lettere di questo alfabeto sono molto più fini di quelle di una lingua: ognuna copre due centesimi di secondo, meno di quanto duri una vocale pronunciata per intero, quindi per dire una «a» ce ne vogliono parecchie di fila. L’elenco se lo costruisce lui stesso, ed è la parte che stona: come fa a scriverlo, se non sa ancora niente del suono? Lo scrive male, all’inizio, e lo riscrive man mano che impara, proprio come si impara a riconoscere una lingua straniera prima di sapere quali suoni conti distinguere. Sotto la parte coperta c’è una di quelle unità, e il gioco è indovinare quale: gli si mette davanti quella giusta insieme a un centinaio di unità sbagliate (i «distrattori») e deve solo riconoscerla. È un test a risposta multipla, e per rispondere bene l’orecchio è costretto a capire come è fatto il parlato.
Una regola tiene in piedi il gioco: le lettere di quell’alfabeto vanno usate tutte. Se il modello se la cavasse con tre, appiccicate a qualunque suono, sotto la parte coperta e fra i distrattori finirebbe sempre la stessa cosa, e da un test con tutte le risposte uguali non si impara niente.
Dopo aver ascoltato in questo modo decine di migliaia di ore di audio senza etichette, a wav2vec 2.0 bastano appena dieci minuti di parlato trascritto per imparare a riconoscere la voce con una qualità che, solo pochi anni prima, richiedeva centinaia di ore.
Quel numero però viene raccontato a metà. Il modello che ha imparato ad ascoltare non ci arriva da solo: accanto a lui lavora un secondo modello, che non ascolta niente, sa soltanto com’è fatta la lingua e scarta le parole improbabili. Il risultato è della coppia. Ascoltare montagne di audio risolve il problema di quante trascrizioni servono; non insegna l’italiano.
L’architettura ha tre stadi. Un encoder convoluzionale \(f\) trasforma la forma d’onda grezza \(\mathbf{x}\) in una sequenza di vettori latenti \(\mathbf{Z} = (\mathbf{z}_1, \dots, \mathbf{z}_T)\), uno ogni ~20 ms. Un Transformer \(g\) legge \(\mathbf{Z}\) (con alcuni tratti mascherati) e produce rappresentazioni contestuali \(\mathbf{C} = (\mathbf{c}_1, \dots, \mathbf{c}_T)\), in cui ogni \(\mathbf{c}_t\) tiene conto dell’intera frase. In parallelo, un modulo di quantizzazione sostituisce ogni \(\mathbf{z}_t\) con una voce di un dizionario appreso (in gergo, product quantization: due codebook da 320 voci ciascuno, e le due voci scelte si concatenano). Piccoli sono i due codebook, non l’alfabeto che ne esce: le combinazioni possibili sono \(320^2 = 102\,400\). La concatenazione passa poi per una trasformazione lineare, che è il passaggio che la porta nello stesso spazio di \(\mathbf{c}_t\) e senza il quale il confronto fra i due non si potrebbe nemmeno fare; il risultato è il bersaglio discreto \(\mathbf{q}_t\), cioè il modo di darsi un «alfabeto» finito di unità di suono senza definirlo a mano. Le sue voci sono più corte dei fonemi: ce n’è una ogni 20 ms.
Attenzione a come avviene la scelta, perché non è quella che verrà definita nella sezione sui codec neurali: qui non si cerca l’entrata più vicina in distanza. \(\mathbf{z}_t\) viene proiettato su una griglia di \(G \times V\) logit (con \(G = 2\) gruppi e \(V = 320\) voci per gruppo) e l’indice è l’\(\arg\max\) della Gumbel-softmax di quei logit, cioè della softmax dei logit perturbati con rumore di Gumbel e temperatura \(\tau\). A rendere stocastica la scelta è il rumore, non la temperatura: dividere per \(\tau > 0\) è una riscalatura monotòna e l’\(\arg\max\) non se ne accorge. \(\tau\) agisce all’indietro, sul gradiente, ed è per questo che il paper la fa scendere lungo l’addestramento: da 2 a 0,5 nella versione base, e fino a 0,1 in quella grande, che è poi quella dei numeri più sotto. Il termine di diversità, invece, non la vede: gli autori lo scrivono sulla softmax nuda dei logit, dichiarando che lì dentro non c’è né il rumore di Gumbel né la temperatura. All’indietro si usa lo straight-through, che rende derivabile una scelta discreta: senza i logit non ci sarebbe niente su cui scriverlo.
L’obiettivo è contrastivo. Per ogni passo mascherato \(t\), dato il vettore contestuale \(\mathbf{c}_t\), il modello deve riconoscere la vera unità quantizzata \(\mathbf{q}_t\) in mezzo a un insieme \(\mathcal{Q}_t\) formato da \(\mathbf{q}_t\) e da \(K\) distrattori (nel paper, \(K = 100\); è la \(K\) del contrastivo, e non ha niente a che vedere con le \(K\) voci del codebook della sezione sui codec) pescati da altri passi mascherati:
È la perdita InfoNCE, la stessa che il libro ha già montato per le immagini e per la coppia immagine-testo [vdOLV18], con l’audio al posto delle une e dell’altra. Qui \(\mathrm{sim}(\mathbf{a},\mathbf{b})\) è la similarità del coseno (già usata per gli embedding) e \(\mathcal{Q}_t\) l’insieme dei candidati; \(\kappa\) è la temperatura del contrastivo, e il nome è quello del paper, che la \(\tau\) l’aveva già spesa per la Gumbel-softmax. Altrove la stessa temperatura si scrive \(\tau\), ed è lì che si inciampa. È una softmax che premia il modello quando assegna a \(\mathbf{q}_t\) la probabilità più alta. Un secondo termine di diversità incoraggia a usare tutte le voci del dizionario, e la ragione la dà il paper: se il dizionario collassa su poche voci, il bersaglio e i distrattori diventano la stessa cosa e il compito degenera. A valle, con una testa CTC su pochissime etichette, la versione grande di wav2vec 2.0 raggiunge un tasso di errore sulle parole (in sigla WER, word error rate: la quota di parole da correggere per rimettere a posto la trascrizione, e il capitolo sullo Speech Recognition la costruisce da capo) di \(4{,}8/8{,}2\) usando 10 minuti di parlato trascritto e 53.000 ore non etichettate, che vengono da un corpus di audiolibri più grande di quello di prova [BZMA20]. I due numeri sono le due prove d’esame di Librispeech, test-clean e test-other: la seconda è quella difficile, con registrazioni e accenti più ostici, e infatti l’errore è quasi sempre più alto.
Quel numero però va letto per intero, ed è la cifra più citata del paper: lo stesso abstract la dà senza dire che è ottenuta decodificando con un modello di lingua Transformer. Il solo modello acustico, nella stessa configurazione, sta a \(40{,}2/38{,}7\) (la tabella in appendice del paper smonta il contributo della decodifica; e sì, a quel regime le due misure si scambiano, che è il segno di quanto il modello acustico da solo sia fuori scala); con un modello di lingua a 4-grammi si passa a \(6{,}6/10{,}3\), e solo con quello Transformer si arriva a \(4{,}8/8{,}2\). Fra il primo e l’ultimo l’errore si divide per otto sul test pulito e per quasi cinque su quello difficile. Il pre-addestramento risolve il problema delle etichette acustiche, non sostituisce il modello di lingua: è una distinzione che il capitolo sullo Speech Recognition riprenderà pari pari, quando metterà in fila i pezzi di una pipeline di riconoscimento.
Il cuore del compito si vede in poche righe di NumPy, e la domanda a cui risponde è semplice: il modello punta sull’unità giusta o su uno dei distrattori? Ogni candidato è un gruppetto di numeri. Per misurare quanto somiglia a ciò che il modello si è fatto in mente del pezzetto coperto si calcola un solo numero, che vale 1 quando i due gruppetti dicono la stessa cosa, 0 quando non hanno niente in comune e scende fino a \(-1\) quando dicono il contrario: si chiama similarità del coseno. I cinque punteggi vengono poi riscalati in modo che sommino a uno, così si leggono come probabilità: quanta fiducia il modello mette su ciascun candidato.
import numpy as np
rng = np.random.default_rng(0)
d = 8 # quanti numeri ha ogni gruppetto (nei modelli veri sono centinaia)
# c: quello che il modello si e' fatto in mente del pezzetto COPERTO.
# In un modello ben addestrato e' vicino all'unita' giusta e lontano dai distrattori.
c = rng.standard_normal(d)
# q_true: l'unita' corretta (qui una versione "vicina" a c);
# i distrattori sono unita' pescate da altri pezzetti coperti della stessa frase.
q_true = c + 0.3 * rng.standard_normal(d)
q_dist = rng.standard_normal((4, d))
candidati = np.vstack([q_true, q_dist]) # (5, d): il vero piu' 4 distrattori
def coseno(a, B): # coseno tra a e ogni riga di B
a = a / np.linalg.norm(a)
B = B / np.linalg.norm(B, axis=1, keepdims=True)
return B @ a
kappa = 0.1 # "temperatura": piu' e' bassa,
# piu' la scelta esce netta
punteggi = coseno(c, candidati) / kappa
prob = np.exp(punteggi - punteggi.max())
prob /= prob.sum() # softmax: i punteggi riscalati
# cosi' che sommino a uno
print("prob. per candidato:", prob.round(3))
print("scelto:", int(prob.argmax()), "(0 = unita' giusta)")
prob. per candidato: [0.672 0. 0. 0.271 0.056]
scelto: 0 (0 = unita' giusta)
L’unità giusta vince, ma il margine merita uno sguardo: si prende due terzi della probabilità, e un distrattore pescato a caso se ne prende un quarto. Il conto non ha difetti: i gruppetti di numeri, qui, sono cortissimi.
Vale una regola che tornerà spesso: più numeri ha un gruppetto, più è difficile che due gruppetti pescati a caso si somiglino. La ragione è che somigliarsi vuol dire andare d’accordo su tutti i numeri insieme: con due numeri azzeccarci per caso capita spesso, con cinquecento bisognerebbe azzeccarli tutti e cinquecento, e il caso non ci arriva. Qui ne abbiamo otto, che è pochissimo, ed è il motivo per cui un distrattore preso a caso finisce quasi addosso al bersaglio.
Nel modello vero i numeri sono centinaia, e allora due gruppetti a caso non si somigliano quasi mai: un distrattore qualunque si scarterebbe senza fatica. Il compito resta difficile lo stesso, ma per un’altra ragione, e conviene tenerla presente. I distrattori veri non sono presi a caso: sono unità pescate da altri punti coperti della stessa frase, quindi suoni imparentati con quello da indovinare. E sono cento, non quattro.
HuBERT: darsi le etichette da soli#
Il gioco di wav2vec 2.0 funziona, ma poggia tutto su una cosa delicata: l’elenco di pezzetti-tipo in mezzo a cui il modello deve riconoscere quello giusto. Se quell’elenco è fatto male il gioco premia la risposta sbagliata, e costruirlo bene mentre lo si sta già usando è tutt’altro che semplice. Nel 2021 Wei-Ning Hsu e colleghi, sempre a Facebook AI, propongono con HuBERT (Hidden-Unit BERT) una strada diversa e sorprendentemente semplice [HBT+21]: invece di riconoscere l’unità giusta tra distrattori, darsi da soli delle pseudo-etichette e imparare a predirle, esattamente come BERT predice la parola mascherata. Il giro completo, con i numeri delle due passate, è in Fig. 22.6.
Fig. 22.6 L’anello che si morde la coda, e che proprio per questo funziona. La prima volta i gruppi si fanno su misure grezze del suono e vengono come vengono; addestrato su quelle etichette, il modello si costruisce rappresentazioni migliori, e su quelle i gruppi si rifanno più fini. Il cerchio si percorre due volte.#
Come si scrive una lingua che non ha alfabeto? Te ne inventi uno provvisorio: raggruppi i suoni che ti sembrano simili e dai a ogni gruppo un simbolo («suono numero 1», «suono numero 2»), etichette rozze, inventate da te. Poi giochi al solito gioco della parola coperta: nascondi dei tratti di audio e ti alleni a indovinare quale simbolo c’era sotto. Il bello arriva dopo: quando ti sei fatto l’orecchio, i tuoi raggruppamenti diventano più sensati di quelli di partenza, e allora rifai l’alfabeto con quelli e ricominci. Un ciclo che si affina da solo, come uno schizzo ripassato più volte a matita finché il disegno emerge.
Non serve che l’alfabeto sia giusto: serve che sia coerente, cioè che dia lo stesso simbolo a suoni davvero simili. Se la stessa «sss» finisse ora sotto un simbolo ora sotto un altro, a caso, ti alleneresti a indovinare l’imprevedibile e non ne verrebbe fuori niente. Quando invece i gruppi tengono, azzeccare il simbolo coperto costringe a capire come è fatto il suono, anche se quei nomi te li sei inventati tu.
HuBERT alterna due passi. Passo di clustering (offline): si estraggono feature dall’audio e le si raggruppa con un semplice k-means, ottenendo per ogni frame un’etichetta discreta \(u_t \in \{1, \dots, C\}\), l’«unità nascosta», dove \(C\) è il numero di cluster ed è l’intero inventario discreto. La lettera è quella del paper, e tiene separato questo conto dalla \(V\) di wav2vec 2.0, che conta le voci di uno dei due codebook: là l’inventario è il prodotto dei due, centomila voci abbondanti, qui è \(C\) e basta. La lettera è diversa apposta rispetto a \(\mathbf{z}_t\): qui \(u_t\) è un intero, un nome di gruppo, mentre lo \(\mathbf{z}_t\) di wav2vec 2.0 è un vettore di numeri reali. È la differenza di fondo fra i due metodi, e si vede nei simboli. Nella prima iterazione le feature sono banali MFCC; nelle successive si usano le rappresentazioni interne del HuBERT già addestrato, che danno cluster via via migliori. I numeri del paper: cento cluster su MFCC alla prima iterazione, cinquecento sulle uscite del sesto strato del Transformer alla seconda. Passo di predizione mascherata: si maschera un sottoinsieme \(M\) di frame e si addestra il modello, alla BERT, a predire le pseudo-etichette dei frame mascherati:
dove \(\tilde{\mathbf{X}}\) è la sequenza di frame con i tratti mascherati, \(u_t\) l’unità nascosta assegnata dal k-means al frame \(t\) e \(p_\theta\) la distribuzione, prodotta dal modello, sulle \(C\) unità del dizionario. La somma sui soli frame mascherati è la mossa principale del lavoro, non una semplificazione di comodo: la forma generale pesa anche i frame scoperti, e gli autori misurano che prendere solo i mascherati è ciò che fa funzionare il metodo. Come obiettivo è una normale cross-entropia su un problema di classificazione, senza distrattori né contrastivo; il coseno e la temperatura, però, ci sono anche qui, perché \(p_\theta\) confronta l’uscita del modello con vettori appresi, uno per unità.
Perché funziona pur partendo da etichette rozze? Perché ciò che conta non è la correttezza del clustering ma la sua coerenza: se il k-means assegna lo stesso simbolo a frame acusticamente simili, predire quel simbolo forza il modello a modellare la struttura del segnale. E l’iterazione chiude il cerchio: rappresentazioni migliori \(\to\) cluster migliori \(\to\) bersagli migliori. A parità di condizioni HuBERT sta appaiato a wav2vec 2.0 nei regimi a basse risorse su Librispeech: a dieci minuti di etichette fa \(4{,}7/7{,}6\) contro \(4{,}8/8{,}2\), cioè un decimo di punto sul pulito e sei decimi sul difficile, e a cento ore gli autori dichiarano da sé due casi in cui resta indietro di un decimo. Il salto vero lo fa il modello da un miliardo di parametri, che è un’altra taglia [HBT+21].
I due si somigliano più di quanto sembri. Dentro sono fatti allo stesso modo, e il motore è identico: coprire dei pezzi di audio e costringere il modello a tirare fuori quello che c’era sotto. Cambia il bersaglio, cioè che cosa esattamente gli si chiede di indovinare. Uno gliela fa riconoscere in mezzo a dei distrattori, come in un test a crocette; l’altro gli chiede di dirne il nome, e i nomi possibili sono quelli dell’alfabeto provvisorio.
E cambia anche quando il bersaglio viene deciso. wav2vec 2.0 se lo costruisce mentre impara, con lo stesso addestramento che poi lo deve indovinare: l’elenco si muove sotto i piedi del gioco. HuBERT invece se lo prepara a parte, prima di cominciare, e lo rifà solo ogni tanto: mentre si gioca, l’elenco sta fermo.
A cosa servono#
Queste rappresentazioni pre-addestrate sono diventate un mattone di buona parte dei sistemi audio moderni. Il caso di scuola è il riconoscimento vocale, in sigla ASR, dall’inglese automatic speech recognition, che è il mestiere a cui il capitolo sullo Speech Recognition è dedicato per intero.
Serve soprattutto dove le trascrizioni scarseggiano: una lingua parlata da poche persone, un dialetto, un mestiere di cui nessuno ha mai raccolto registrazioni annotate. Si parte da un modello che ha ascoltato montagne di audio senza etichette, gli si mostrano le poche ore trascritte che esistono, e si arriva a risultati che prima erano impensabili. Il collegamento con il capitolo sullo Speech Recognition è diretto: la parte che lì trasformerà le rappresentazioni in parole non fa che rifinire ciò che il pre-addestramento ha già preparato.
Gli stessi numeri servono poi a classificare suoni ambientali, a identificare chi parla, a riconoscere emozioni o lingua, e (come vedremo nelle prossime due sezioni) fanno da punto di partenza anche per la generazione di audio: i pezzetti-tipo imparati qui diventano un vocabolario su cui un modello può «scrivere» suono, come un modello linguistico scrive testo.
Queste rappresentazioni colgono benissimo i suoni e come si incastrano fra loro: quali sono, in che ordine, con che timbro. È esattamente ciò che il gioco della parte coperta premia, e non c’è da stupirsi.
Colgono molto meno, però, il significato. Un modello addestrato così sa che due frammenti suonano simili, non sa se una frase è ironica o se una domanda vuole una certa risposta. È un orecchio finissimo, non una mente che comprende. Il senso lo mettono i pezzi che vengono dopo, che su questo orecchio si appoggiano. Il pre-addestramento audio risolve il problema delle etichette, non quello della comprensione: distinguere le due cose è il primo passo per usarlo bene.
Da ricordare
Trascrivere l’audio costa; di audio non trascritto ce n’è a valanga. Un modello può imparare da solo com’è fatto il suono (come il bambino che sente la lingua prima di saperla scrivere) e solo dopo imparare il compito vero con poche ore di esempi corretti.
Quello che impara si chiama rappresentazione: il gruppetto di numeri con cui si tiene in mente un pezzetto di suono, fatto in modo che pezzetti simili finiscano vicini.
wav2vec 2.0 gioca al gioco della parola coperta: nasconde dei tratti di audio e chiede di riconoscere quello giusto in mezzo a qualche distrattore, come un test a crocette. Con dieci minuti di parlato trascritto arriva dove prima servivano centinaia di ore, purché ad aiutarlo ci sia anche un modello che sa com’è fatta la lingua.
HuBERT cambia gioco: si inventa un alfabeto provvisorio raggruppando i suoni che si somigliano, poi si allena a indovinare quale simbolo stava sotto la parte coperta, e ogni tanto rifà l’alfabeto meglio di prima. Non serve che sia giusto, serve che sia coerente.
Questo orecchio è finissimo ma non è una mente: sa che due frammenti suonano simili, non sa se una frase è ironica. Il significato lo mettono i pezzi che vengono dopo.
Da ricordare
Etichettare l’audio è costoso, ma di audio non etichettato ce n’è a valanga: l’apprendimento auto-supervisionato impara la struttura del suono da solo (pretraining), poi rifinisce sul compito vero con poche etichette (fine-tuning) (lo stesso salto che nel testo va da word2vec a BERT).
wav2vec 2.0 [BZMA20]: encoder convoluzionale + Transformer, i latenti sono quantizzati in unità discrete, e mascherando parti del segnale il modello impara con un obiettivo contrastivo a riconoscere l’unità giusta tra distrattori (il cloze test del suono). La scelta dell’unità passa per una Gumbel-softmax sui logit, non per la distanza dal prototipo più vicino. Con 10 minuti di etichette raggiunge un WER di \(4{,}8/8{,}2\) su Librispeech, ma con un modello di lingua Transformer in decodifica: il solo modello acustico sta intorno al 40 %.
HuBERT [HBT+21]: niente contrastivo, ma pseudo-etichette da un k-means (unità nascoste) predette sui frame mascherati, con iterazione che raffina i cluster. Conta la coerenza dei bersagli, non la loro correttezza.
Le due condividono l’ossatura e differiscono nel bersaglio: riconoscere (contrastivo) contro predire una classe (masked prediction).
Queste rappresentazioni sono il mattone di ASR a basse risorse, classificazione audio e generazione; catturano bene fonetica e struttura, molto meno il significato ad alto livello.