Scrivere il mio codice di riconoscimento vocale [chiuso]


17

Descrizione del problema

Voglio usare il riconoscimento vocale come parte di un progetto hardware, che vorrei essere completamente autonomo (sto usando piccoli dispositivi a bassa potenza e bassa velocità come Arduino e Raspberry Pi, Kinects ecc., Nessun computer tradizionale con è coinvolto un sistema operativo, quindi un progetto chiuso / che contiene).

Il riconoscimento vocale può essere molto complicato a seconda del livello di raffinatezza che desideri. Ho quello che credo un insieme relativamente semplice di requisiti. Voglio solo riconoscere la mia voce e ho un piccolo dizionario di circa 20 parole che vorrei riconoscere. Quindi non ho bisogno di complesse librerie di riconoscimento vocale e vocale o di nessuno degli eccellenti software di terze parti che trovo tramite i motori di ricerca di Internet (non mancano questi!). Credo che i miei requisiti siano "abbastanza semplici" (entro limiti ragionevoli) da poter codificare la mia soluzione. Mi chiedo se qualcuno ha scritto il proprio processo in questo modo, e il mio metodo è enormemente difettoso? Esiste un modo migliore per farlo senza richiedere un alto livello di matematica o senza dover scrivere un algoritmo complesso? Questa è la soluzione che ho provato a pensare di seguito.

Descrizione della soluzione

Scriverò questo in C ma vorrei discutere di un processo agnostico linguistico, focalizzandomi sul processo stesso. Quindi, se possibile, ignoriamolo.

1 Pre-registrerò il mio dizionario di parole per abbinare quelle pronunciate. Possiamo immaginare di avere 20 registrazioni delle mie 20 parole diverse, o forse brevi frasi o frasi di due o tre parole. Credo che ciò renda il processo di confronto tra due file di registrazione più semplice della conversione effettiva dell'audio in testo e del confronto di due stringhe.

2 Un microfono è collegato al mio dispositivo hardware che esegue il mio codice. [1]. Il codice prende continuamente campioni di lunghezza fissa, ad esempio 10msec di lunghezza, e memorizza 10 campioni consecutivi, ad esempio, in uno stile di registrazione circolare. [2]. (Sto inventando queste figure dalla parte superiore della mia testa, quindi sono solo esempi per descrivere il processo).

[1] Ciò verrebbe probabilmente collegato attraverso un filtro passa-banda e un amplificatore operazionale, così come le registrazioni del dizionario, per ridurre i campioni audio memorizzati e raccolti.

[2] Non sono sicuro di come prenderò un campione, ho bisogno di elaborare un metodo anche se produco una cifra numerica (intero / float / doppio) che rappresenta l'audio di un campione da 10 msec (forse un valore CRC o somma MD5 ecc. del campione audio), o un flusso di cifre (forse un flusso di letture audio delle frequenze). Alla fine un "campione" sarà una o più cifre numeriche. Questa parte coinvolgerà molto più hardware, quindi non è proprio da discutere qui.

3 Il codice osserva che sono memorizzati 10 campioni consecutivi e cerca un aumento di volume per indicare che una parola o una frase viene detta (una pausa dal silenzio) e quindi aumenta la raccolta di campioni consecutivi per dire, ad esempio, 500 campioni. Ciò significherebbe che cattura 5 secondi di audio in campioni da 10 msec.

Sono questi campioni o "sezioni" che vengono confrontati tra il suono memorizzato e il suono acquisito. Se una percentuale sufficientemente elevata di campioni catturati corrispondeva a quelli archiviati equivalenti, il codice assume la stessa parola.

The start of a store recording of the world "hello" for example,
stored words are split into 10 msec samples also

Stored Sample No           | 1| 2| 3| 4| 5| 6| 7|  8|
Stored Sample Value        |27|38|41|16|59|77|200|78|

Incoming audio (me saying "hello") with some "blank" samples
at the start to symbolise silence

Incoming Sample No         | 1| 2| 3| 4| 5| 6| 7| 8| 9|10| 11|12|
Incoming Sample Value      |  |  |  |20|27|38|46|16|59|77|200|78|

4 Una volta che il codice ha raccolto un flusso di campionamento completo, all'inizio taglia i campioni di spazi vuoti per produrre la seguente registrazione audio. Potrebbe anche spostare il set di campioni avanti e indietro di alcuni punti per allinearlo meglio con il campione memorizzato.

Questo produce un set di esempio come il seguente:

Stored Sample No           | 1| 2| 3| 4| 5| 6|  7| 8|
Stored Sample Value        |27|38|41|16|59|77|200|78|

Incoming Sample No      |-1| 1| 2| 3| 4| 5| 6|  7| 8|
Incoming Sample Value   |20|27|38|46|16|59|81|201|78|

5Credo che avendo un valore percentuale per quanto deve essere vicino ogni campione, quindi il campione 7 differisce per un valore 1 che è inferiore a% 1 e un valore percentuale per il numero totale di campioni che devono essere all'interno della loro percentuale di corrispondenza del campione , il codice ha un livello di precisione facilmente sintonizzabile.

Non ho mai fatto nulla di simile con l'audio prima, potrebbe essere un sacco di lavoro. Questo è il motivo per cui sto ponendo questa domanda, se forse conosci già la risposta a questa domanda per essere ovvia (qualunque cosa possa mai essere quella risposta). Spero che questo non sia un compito enorme dal punto di vista computazionale dato che parte dell'hardware che userò sarà roba da pochi secondi. Nelle centinaia di Megahertz (forse 1Ghz usando un Rasp Pi over-clock). Quindi questo è un modo piuttosto grezzo per abbinare campioni audio usando una potenza computazionale inferiore. Non sto puntando a risultati immediati, ma meno di 30 secondi per una prova decente del concetto.

PS Non ho il rappresentante per taggare questo con un nuovo tag come "audio", "riconoscimento audio", "voce", "riconoscimento vocale" ecc.


17
La realtà virtuale è piuttosto complessa e dubito che qualcuno senza conoscenza sul campo sarà in grado di fare molti progressi senza molta lettura. La prima cosa che mi colpisce del tuo algoritmo è che non gestirà le differenze nella velocità con cui una parola viene pronunciata. Anche la semplice VR ha impiegato anni per avere ragione.
Gort il robot il

4
Infatti. A meno che non ti dispiaccia anni di sviluppo, potresti voler esaminare le librerie che puoi compilare per il tuo obiettivo. Sono sicuro che esistono.
Rig

6
Suggerirei un passaggio aggiuntivo: esegui una trasformazione di Fourier di ciascun campione. Questo ti dà l'intensità di ogni frequenza audio nel tempo, piuttosto che gestire direttamente i campioni. Ci sarà una frequenza fondamentale ragionevolmente coerente per le vocali che normalmente parli a cui potresti rilevare. Devi guardare le caratteristiche specifiche del parlato, non solo l'audio. Come altri hanno già detto, questo è un compito difficile.
Paul Anderson,

1
Ti suggerirei di provare a giocare con alcune librerie di riconoscimento vocale, anche se non puoi usarle per il prodotto finale. Sarebbero utili per creare una prova di concetto.
salva il

Risposte:


3

Beh, non credo che l'Arduino abbia il potere di cavallo per farlo. funziona a 16Mhz Un Arduino ha circa 32K di memoria. Perfino 20 parole campionate in Mp3 (più piccolo di allora) non ci starebbero, nonostante sia solo la tua voce.

Il rasberi pi potrebbe fare il trucco, funzionando a 700Mhz a seconda della versione potrebbe avere una memoria di 512 MB. Non è ancora molto impasto.

Potrebbe essere necessario un Fourier ( http://www.drdobbs.com/cpp/a-simple-and-efficient-fft-implementatio/199500857 )

Oppure, se si intende utilizzare il volume, fare alcune medie con campioni precedenti come
x = (x + x [n-1] + x [n-2] + x [n-3]) / 4 // è abbastanza semplice bisogno di piu

La prossima cosa che devi fare è penso che se dovessi tracciare questi valori X, allora hai bisogno di un qualche tipo di rilevamento della pendenza di quella linea Perché rilevare comandi basati sul volume dipende altrimenti molto dalla distanza Mentre preferisci rilevare il modello di le parole

Quindi dipende un po 'come registrare la pendenza in modo che il motivo si adatti un'altra volta. Voglio dire, non si parla nel tempo esatto che un computer può eguagliare e la pendenza può essere un po 'più ripida. Alla fine penso che sia un po 'ripido quanto queste linee e il loro asse y di lunghezza dovrebbero essere nella media


1
  1. Arduino e Raspberry Pi sono schede di prototipazione con piccoli chip su di esse. Dovresti prima concentrarti sul chip. Cerca qualcosa con un toolbox DSP (digital signal processing), forse hai già un toolbox DSP e non lo sai. Le cassette degli strumenti DSP hanno algoritmi su chiamata come fft (trasformata veloce di Fourier) e ifft (inversa fft) per l'analisi rapida del dominio di frequenza.

  2. Concentrati sul tuo stile programmatico: i tuoi campioni sono in una pila o in una coda? Avrai bisogno di una coda per questo tipo di dati. Una coda assomiglia a:

    Position NO --|1|2|3|4|5|6|7|8|
    Sample Value  |5|7|9|1|2|2|9|8|
    

    Prossima iterazione:

    Position NO --|1|2|3|4|5|6|7|8|
    Sample Value  |0|5|7|9|1|2|2|9|
    ->  First in First out (FIFO)
    

    Notate come le cose si spostano verso il "giusto"? Penso che tu abbia descritto un algoritmo "circolare". Basta sovrascrivere i campioni più vecchi con i secondi campioni più vecchi, quindi sovrascrivere i secondi campioni più vecchi con il terzo più vecchio, ..., fino all'inizio della coda in cui si inseriscono i dati più recenti.

  3. "Il codice preleva continuamente campioni a lunghezza fissa, diciamo 10msec" <- errato Pensa in questo modo: il codice sta prendendo discretamente campioni quantizzati (altezza), a una frequenza di campionamento di 10000 campioni al secondo, il che rende ogni campione distanziato di 0,1 ms.

    Qual è la tua frequenza di campionamento? Qual è il bitrate sul tuo quantizzatore? Numeri più bassi ti aiuteranno a liberare memoria. Suggerirei una bassa frequenza di campionamento come 6600 campioni al secondo (Nyquist). Sospetto che 4 bit (16 livelli) sarebbero sufficienti per il riconoscimento. Quindi sono 3300 byte di registrazione al secondo. Ora esegui fft ed elimina tutto sopra i 3300 Hz (filtro di telefonia). Ora hai 1650 byte usati per un secondo di suono. Questi trucchi DSP risparmieranno molta memoria.

    Non so chi pensi che 512 MB siano piccoli. Con le informazioni di cui sopra che sono oltre 300.000 secondi di registrazione ... oltre 3 giorni solidi.

  4. Penso che troverai il dominio della frequenza (usando fft) come un ambiente migliore per eseguire il riconoscimento vocale.

Spero di non averti confuso peggio :)

Utilizzando il nostro sito, riconosci di aver letto e compreso le nostre Informativa sui cookie e Informativa sulla privacy.
Licensed under cc by-sa 3.0 with attribution required.