Comment tout a commencé
Tout a commencé avec Apple Market - j'ai découvert qu'ils avaient un programme pour déterminer la maturité d'une pastèque. Le programme ... est bizarre. Que vaut, au moins, l'offre de frapper sur une pastèque non pas avec vos phalanges, mais ... par téléphone! Néanmoins, je voulais répéter cet exploit sur une plate-forme Android plus familière.
Sélection d'outils
Notre problème est résolu de plusieurs manières, et pour être honnête, j'ai dû faire des efforts considérables pour ne pas suivre la voie "simple". Autrement dit, prenez des transformées de Fourier, des ondelettes et un éditeur de signaux. Cependant, je voulais acquérir de l'expérience avec les réseaux de neurones, alors laissez les réseaux faire l'analyse des données.
Keras, le module complémentaire Google pour TensorFlow et Theano, a été choisi comme bibliothèque pour créer et former des réseaux de neurones. En général, si vous débutez avec les réseaux d'apprentissage en profondeur, il vaut mieux ne pas trouver d'outil. D'une part, Keras est un outil puissant optimisé pour la vitesse, la mémoire et le matériel (oui, il peut fonctionner sur les cartes vidéo et leurs clusters). D'un autre côté, tout ce qui peut être «caché» à l'utilisateur y est caché, vous n'avez donc pas besoin de faire travailler votre cerveau sur l'amarrage des couches d'un réseau de neurones, par exemple. Très confortable.
Comme Keras, et les réseaux de neurones en général, nécessitent une connaissance de Python - ce langage, comme un serpent enroulé autour ... désolé, refoulé. En bref, vous ne devriez pas vous mêler du Deep Learning moderne sans Python. Heureusement, Python peut être étudié en deux semaines, dans des cas extrêmes - en un mois.
Vous aurez besoin de plus de bibliothèques pour Python, mais ce sont des trivialités - je veux dire, si vous avez traité Python lui-même. Cela nécessitera une connaissance (très superficielle) de NumPy, PyPlot et, éventuellement, de quelques bibliothèques, dont nous prenons littéralement quelques fonctions. Pas difficile. La vérité est.
Eh bien, en conclusion, je note que nous n'avons pas besoin des clusters de cartes vidéo mentionnés ci-dessus - notre tâche est normalement résolue à l'aide d'un processeur d'ordinateur - lentement, mais pas de manière critique.
Plan de travail
Vous devez d'abord créer un réseau de neurones - sur Python et Keras, sous Ubuntu. Vous pouvez - sur l'émulateur Ubunta. Vous pouvez - pour Windows, mais le temps supplémentaire passé vous suffit pour étudier l'Ubuntu mentionné, puis y travailler.
L'étape suivante consiste à écrire un programme. Je prévois de le faire en Java sous Android. Ce sera un prototype du programme, dans le sens où il aura une interface utilisateur, mais il n'y a pas encore de réseau neuronal.
Quel est le sens de l'écriture de «sucettes», demandez-vous. Mais voici la chose: toute tâche liée à l'analyse des données, tôt ou tard, repose sur la recherche de données - pour la formation de notre programme. En fait, combien de pastèques devraient être exploitées et dégustées pour que le réseau neuronal puisse construire un modèle fiable sur ces données? Une centaine? Plus?
Ici, notre programme nous aidera: téléchargez-le sur Google Play, distribuez (d'accord, imposez, tordez les bras) à tous vos amis qui n'ont pas la chance d'avoir un téléphone avec Android, et les données, un minuscule flux, commencent à couler ... et au fait, où?
L'étape suivante consiste à écrire un programme serveur qui reçoit des données de notre client Android. Certes, ce programme serveur est très simple, j'ai tout fini en une vingtaine de minutes. Mais, néanmoins, il s'agit d'une étape distincte.
Enfin, suffisamment de données. Nous formons un réseau neuronal.
Nous portons le réseau neuronal en Java et publions une mise à jour de notre programme.
Bénéfice Mais non. Le programme était gratuit. Seulement de l'expérience et des bosses farcies.
Création d'un réseau de neurones
Travailler avec l'audio, qui, bien sûr, touche une pastèque, est soit un réseau neuronal récurrent, soit le soi-disant réseau convolutionnel unidimensionnel. De plus, au cours des dernières années, les réseaux évolutifs ont été sans équivoque en tête, remplaçant les réseaux récurrents. L'idée d'un réseau convolutionnel est que la fenêtre glisse sur le tableau de données - le graphique «intensité sonore - temps» - et au lieu d'analyser des centaines de milliers d'échantillons, nous ne travaillons qu'avec ce qui entre dans la fenêtre. Les couches suivantes combinent et analysent les résultats de cette couche.
Pour le rendre plus clair, imaginez que vous devez trouver une mouette sur une photo d'un paysage marin. Vous scannez une image - la «fenêtre» de votre attention se déplace le long de lignes et de colonnes imaginaires, à la recherche d'une coche blanche. Voici comment fonctionne un réseau convolutionnel 2D, tandis qu'un réseau unidimensionnel balaye le long d'une coordonnée - c'est le meilleur choix si nous avons affaire à un signal audio.
Je note cependant qu'il n'est pas nécessaire de se concentrer sur les réseaux 1D. Comme exercice, j'ai tracé le son et analysé le bitmap résultant comme une image - en utilisant un réseau de convolution 2D. À ma grande surprise, le résultat n'a pas été pire que lors de l'analyse de données «unidimensionnelles brutes».
Le réseau utilisé avait la structure suivante:
model = Sequential() model.add(Conv1D(filters=32, kernel_size=512, strides=3, padding='valid', use_bias=False, input_shape=(nSampleSize, 1), name='c1d', activation='relu')) model.add(Activation('relu', input_shape=(nSampleSize, 1))) model.add(MaxPooling1D(pool_size=(2))) model.add(Conv1D(32, (3))) model.add(Activation('relu')) model.add(MaxPooling1D(pool_size=(2))) model.add(Conv1D(64, (3))) model.add(Activation('relu')) model.add(MaxPooling1D(pool_size=(2))) model.add(Flatten()) model.add(Dense(64)) model.add(Activation('relu')) model.add(Dropout(0.5)) model.add(Dense(nNumOfOutputs))
Ce réseau a deux valeurs de sortie (il prédit deux valeurs): douceur et maturité. La douceur est 0 (non sucré), 1 (normal) et 2 (excellent), et la maturité, respectivement, 0 est trop dur, 1 est ce dont vous avez besoin et 2 est trop mûr, comme le coton avec du sable.
Les notes de l'échantillon de test sont définies par la personne, exactement comment - nous parlerons dans la section sur le programme pour Android. La tâche du réseau neuronal est de prédire quelle note une personne accordera pour une pastèque donnée (selon un robinet).
Écrire un programme
J'ai déjà mentionné que le programme devrait sortir en deux versions. La première, préliminaire, avertit honnêtement l'utilisateur que ses prédictions sont complètement absurdes. Mais il permet à l'utilisateur d'enregistrer un coup sur une pastèque, d'évaluer le goût de cette pastèque et de l'envoyer à l'auteur du programme sur Internet. Autrement dit, la première version collecte simplement des données.
Voici la
page du
programme sur Google Play, bien sûr, le programme est gratuit.
Que fait-elle:
1. Appuyez sur le bouton avec le microphone et l'enregistrement démarre. Vous avez cinq secondes pour frapper la pastèque trois fois - coup-coup-coup. Un bouton avec une pastèque fait une «prédiction», et nous ne la touchons pas encore.
Remarque - si Google a une ancienne version, l'enregistrement et la prédiction sont combinés dans un bouton avec une pastèque, mais il n'y a pas de bouton avec un microphone.

2. Le fichier enregistré est temporaire et sera écrasé la prochaine fois que vous appuierez sur le bouton d'enregistrement. Cela vous permet de répéter le tapotement si quelqu'un parle bras dessus bras dessous (vous ne pouvez pas imaginer à quel point il est difficile de faire taire les autres pendant cinq secondes!) Ou l'eau est bruyante - la vaisselle sonne - le voisin est en train de forer ...
Mais maintenant, la pastèque est sélectionnée et achetée. Vous l'avez ramené à la maison, enregistré un son et coupé. Vous êtes maintenant prêt à évaluer son goût. Sélectionnez l'onglet Enregistrer.
Sur cet onglet, nous voyons deux zones de liste déroulante pour le classement - douceur et maturité (douceur et maturité, le travail de traduction est en cours). Mettez une marque - cliquez sur Enregistrer.
Attention! Enregistrer ne peut être cliqué qu'une seule fois. Alors, mettez d'abord une marque. Au simple toucher d'un bouton, le fichier son est renommé et maintenant il ne sera pas effacé la prochaine fois qu'il sera enregistré.

3. Enfin, après avoir enregistré (et donc mangé) une dizaine de pastèques, vous êtes rentré du chalet, où vous n'aviez pas Internet. Maintenant, Internet l'est. Ouvrez l'onglet Soumettre et appuyez sur le bouton. Le package (avec une douzaine de pastèques) va au serveur du développeur.

Écrire un programme serveur
Tout est simple ici, donc je ferais mieux de disposer le code complet de ce script. Le programme «capture» les fichiers, leur donne des noms uniques et les place dans un répertoire accessible uniquement au propriétaire du site.
<?php if (is_uploaded_file($_FILES['file']['tmp_name'])) { $uploads_dir = './melonaire/'; $tmp_name = $_FILES['file']['tmp_name']; $pic_name = $_FILES['file']['name']; $filename = md5(date('Ymd H:i:s:u')); move_uploaded_file($tmp_name, $uploads_dir.$filename); } else { echo "File not uploaded successfully."; } ?>
Formation au réseau de neurones
Les données sont divisées en formation et test, 70 et 30 pour cent, respectivement. Réseau de neurones - converge. Il n'y a cependant pas de surprise ici pour les débutants: n'oubliez pas de normaliser les données d'entrée, cela vous épargnera beaucoup de nerfs. Quelque chose comme ça:
for file_name in os.listdir(path): nSweetness, nRipeness, arr_loaded = loadData(file_name) arr_data.append(arr_loaded / max(abs(arr_loaded)))
Portage d'un réseau de neurones
Il existe plusieurs façons de porter un réseau d'un environnement Python vers Java. Récemment, Google a rendu ce processus plus pratique, donc si vous lisez les manuels, assurez-vous qu'ils ne sont pas obsolètes. Voici comment je l'ai fait:
from keras.models import Model from keras.models import load_model from keras.layers import * import os import sys import tensorflow as tf
Faites attention à la dernière ligne: dans le code Java, vous devrez spécifier les noms d'entrée et de sortie du réseau. Cette "impression" ne fait que les imprimer.
Donc, nous mettons le fichier reçu coordted.pb dans le répertoire des actifs du projet dans Android Studio, connectons la bibliothèque tensorflowinferenceinterface (voir
ici , ou mieux,
ici ), et c'est tout.
C’est tout. Quand je l'ai fait pour la première fois, je m'attendais à ce que ce soit difficile, mais ... cela a fonctionné du premier coup.
Voici à quoi ressemble un appel de réseau neuronal à partir du code Java:
protected Void doInBackground(Void... params) { try {
Ici m_arrInput est un tableau avec deux éléments contenant - oui! - notre prédiction, normalisée de zéro à un.
Conclusion
Ici, semble-t-il, on est censé remercier de l'attention et exprimer l'espoir que c'était intéressant. Au lieu de cela, je note que Google est la première version du programme. Le second est complètement prêt, mais pas assez de données. Donc, si vous aimez les pastèques - veuillez mettre un programme sur votre Android. Plus vous envoyez de données, meilleure sera la deuxième version ...
Bien sûr, ce sera gratuit.
Bonne chance, et oui: merci d'avoir regardé. J'espère que c'était intéressant.
Mise à jour importante: une nouvelle version avec une analyse améliorée a été publiée. Merci à tous ceux qui ont envoyé les pastèques, et merci d'en envoyer plus!