Description du problème
Je souhaite utiliser la reconnaissance vocale dans le cadre d'un projet matériel, que j'aimerais être complètement autonome (j'utilise de petits appareils à faible puissance et à faible vitesse tels que Arduino et Raspberry Pi, Kinects, etc., sans ordinateur traditionnel avec un OS est impliqué. Donc un projet fermé / autonome).
La reconnaissance vocale peut être très compliquée selon le niveau de sophistication que vous désirez. J'ai ce que je crois un ensemble d'exigences relativement simple. Je veux seulement reconnaître ma propre voix, et j'ai un petit dictionnaire d'une vingtaine de mots que j'aimerais reconnaître. Ainsi, je n'ai pas besoin de bibliothèques complexes de reconnaissance vocale ou vocale ou de l'un des excellents logiciels tiers que je trouve via les moteurs de recherche Internet (ils ne manquent pas!). Je crois que mes exigences sont "assez simples" (dans des limites raisonnables) pour que je puisse coder ma propre solution. Je me demande si quelqu'un a écrit son propre processus comme celui-ci, et ma méthode est-elle massivement défectueuse? Y a-t-il une meilleure façon de le faire sans nécessiter un niveau élevé de mathématiques ou avoir à écrire un algorithme complexe? C'est la solution que j'ai essayé de trouver ci-dessous.
Description de la solution
Je vais écrire ceci en C mais je souhaite discuter d'un processus indépendant du langage, en se concentrant sur le processus lui-même. Ignorons donc cela si nous le pouvons.
1 . Je vais pré-enregistrer mon dictionnaire de mots pour correspondre à ceux parlés. Nous pouvons imaginer que j'ai 20 enregistrements de mes 20 mots différents, ou peut-être de courtes phrases ou phrases de deux ou trois mots. Je crois que cela rend le processus de comparaison de deux fichiers d'enregistrement plus facile que la conversion de l'audio en texte et la comparaison de deux chaînes.
2. Un microphone est connecté à mon périphérique matériel exécutant mon code. [1]. Le code prend continuellement des échantillons de longueur fixe, disons 10 ms de longueur par exemple, et stocke 10 échantillons consécutifs par exemple, dans un style d'enregistrement circulaire. [2]. (J'invente ces chiffres du haut de ma tête donc ce ne sont que des exemples pour décrire le processus).
[1] Celui-ci serait probablement connecté via un filtre passe-bande et un ampli-op, tout comme les enregistrements de dictionnaire, afin de réduire la taille des échantillons audio stockés et collectés.
[2] Je ne sais pas exactement comment je vais prendre un échantillon, je dois trouver une méthode, mais si je produisais un chiffre numérique (entier / flottant / double) qui représente l'audio d'un échantillon de 10 ms (peut-être une valeur CRC ou MD5 somme etc. de l'échantillon audio), ou un flux de chiffres (un flux de lectures audio de fréquences peut-être). En fin de compte, un "échantillon" sera une ou plusieurs figures numériques. Cette partie va impliquer beaucoup plus de matériel, donc pas vraiment pour la discussion ici.
3. Le code regarde qu'il est stocké 10 échantillons consécutifs et recherche une augmentation de volume pour indiquer qu'un mot ou une phrase est en train d'être dit (une pause dans le silence), puis augmente la collecte d'échantillons consécutifs pour dire 500 échantillons par exemple. Cela signifierait qu'il capture 5 secondes d'audio dans des échantillons de 10 ms.
Ce sont ces échantillons ou "tranches" qui sont comparés entre le son stocké et le son capturé. Si un pourcentage suffisamment élevé d'échantillons capturés correspond aux échantillons stockés équivalents, le code suppose qu'il s'agit du même mot.
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. Une fois que le code a collecté un flux d'échantillons complet, il coupe ensuite les échantillons vides au début pour produire l'enregistrement audio suivant. Il pourrait également déplacer le jeu d'échantillons vers l'arrière et vers l'avant à quelques endroits pour mieux l'aligner avec l'échantillon stocké.
Cela produit un ensemble d'échantillons comme ci-dessous:
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|
5. Je crois qu'en ayant une valeur en pourcentage pour la proximité de chaque échantillon, l'échantillon 7 diffère donc d'une valeur de 1 qui est inférieure à% 1 et d'une valeur en pourcentage pour le nombre total d'échantillons qui doit être dans leur pourcentage d'appariement d'échantillon , le code a un niveau de précision facilement réglable.
Je n'ai jamais rien fait de tel avec l'audio auparavant, cela pourrait demander beaucoup de travail. C'est pourquoi je pose cette question, si vous savez peut-être déjà que la réponse à cette question est évidente (quelle que soit cette réponse). J'espère que ce ne sera pas une tâche de calcul énorme car certains des matériels que j'utiliserai seront des trucs à faible sec. Dans les centaines de mégahertz (peut-être 1 GHz en utilisant un Rasp Pi overclocké). C'est donc une façon assez grossière de faire correspondre des échantillons audio en utilisant une puissance de calcul inférieure. Je ne vise pas des résultats instantanés, mais moins de 30 secondes pour une preuve de concept décente.
PS Je n'ai pas le représentant pour marquer cela avec un nouveau tag comme "audio", "reconnaissance audio", "voix", "reconnaissance vocale" etc.