Menu
Gratuitement
Inscription
Maison  /  Maison idéale/ Stylisation d'images à l'aide de réseaux de neurones : pas de mysticisme, juste des grossièretés. Ostagram : un service basé sur un réseau neuronal qui combine des photos et des ornements dans des chefs-d'œuvre artistiques. Cartes de saillance à l'aide de la rétropropagation guidée.

Stylisation d'images à l'aide de réseaux de neurones : pas de mysticisme, juste des grossièretés. Ostagram : un service basé sur un réseau neuronal qui combine des photos et des ornements dans des chefs-d'œuvre artistiques. Cartes de saillance à l'aide de la rétropropagation guidée.

Dans les photographies les plus ordinaires, apparaissent de nombreuses entités peu distinctes. Le plus souvent, pour une raison quelconque, ce sont des chiens. Internet a commencé à se remplir de telles images en juin 2015, avec le lancement de DeepDream de Google, l'un des premiers services ouverts basés sur des réseaux de neurones et conçus pour le traitement d'images.

Cela se passe à peu près comme ceci : l'algorithme analyse les photographies, y trouve des fragments qui lui rappellent des objets familiers - et déforme l'image en fonction de ces données.

Tout d'abord, le projet a été publié en open source, puis des services en ligne créés selon les mêmes principes sont apparus sur Internet. L'un des plus pratiques et des plus populaires est Deep Dream Generator : traitement de photos petite taille ici, cela ne prend qu'environ 15 secondes (auparavant, les utilisateurs devaient attendre plus d'une heure).

Comment les réseaux de neurones apprennent-ils à créer de telles images ? Et pourquoi, au fait, s’appellent-ils ainsi ?

Les réseaux de neurones dans leur structure imitent les véritables réseaux de neurones d'un organisme vivant, mais faites-le en utilisant algorithmes mathématiques. Après avoir créé une structure de base, vous pouvez la former à l'aide de méthodes d'apprentissage automatique. Si nous parlons de reconnaissance d’images, des milliers d’images doivent passer par un réseau neuronal. Si la tâche du réseau neuronal est différente, alors exercices d'entraînement sera différent.

Les algorithmes pour jouer aux échecs, par exemple, analysent les parties d'échecs. De la même manière, l'algorithme AlphaGo de Google DeepMind a été intégré au jeu de Go chinois - ce qui a été perçu comme une avancée majeure, car le Go est beaucoup plus complexe et non linéaire que les échecs.

    Vous pouvez jouer avec un modèle simplifié de réseaux de neurones et mieux comprendre ses principes.

    Il existe également une série de dessins intelligibles sur YouTube rouleaux sur le fonctionnement des réseaux de neurones.

Un autre service populaire est Dreamscope, qui peut non seulement rêver de chiens, mais également imiter divers styles de peinture. Le traitement des images ici est également très simple et rapide (environ 30 secondes).

Apparemment, la partie algorithmique du service est une modification du programme « Neural style », dont nous avons déjà parlé.

Plus récemment, un programme est apparu qui colore de manière réaliste les images en noir et blanc. Dans les versions précédentes programmes similaires ne faisaient pas aussi bien leur travail, et cela était considéré comme une grande réussite si au moins 20 % des personnes ne pouvaient pas faire la différence entre une image réelle et une image couleur par ordinateur.

De plus, la colorisation ne prend ici qu’environ 1 minute.

La même société de développement a également lancé un service qui reconnaît en images différents types objets.

Ces services peuvent sembler n’être qu’un divertissement amusant, mais en réalité tout est bien plus intéressant. Les nouvelles technologies entrent dans la pratique des artistes humains et changent notre compréhension de l’art. Il est probable que les gens seront bientôt confrontés à la concurrence des machines dans le domaine de la créativité.

Apprendre aux algorithmes à reconnaître les images est une tâche avec laquelle les développeurs se battent depuis longtemps intelligence artificielle. Par conséquent, les programmes qui colorisent de vieilles photographies et dessinent des chiens dans le ciel peuvent être considérés comme faisant partie d’un processus plus vaste et plus intrigant.

Depuis que des chercheurs allemands de l'Université de Tübingen ont présenté leur étude sur la possibilité de transfert de style en août 2015 artistes célèbresà d'autres photos, des services ont commencé à apparaître qui monétisent cette opportunité. Il a été lancé sur le marché occidental et sa copie complète a été lancée sur le marché russe.

Signets

Bien qu'Ostagram ait été lancé en décembre, il a commencé à gagner rapidement en popularité sur les réseaux sociaux à la mi-avril. Dans le même temps, au 19 avril, il y avait moins d'un millier de personnes participant au projet sur VKontakte.

Pour utiliser le service, vous devez préparer deux images : une photo à traiter et une image avec un exemple de style à superposer sur la photo originale.

Le service a version gratuite: Il crée une image avec une résolution minimale allant jusqu'à 600 pixels sur le côté le plus long de l'image. L'utilisateur reçoit le résultat d'une seule des itérations d'application du filtre à la photo.

Il existe deux versions payantes : Premium produit une image jusqu'à 700 pixels sur le côté le plus long et applique 600 itérations de traitement de réseau neuronal à l'image (plus il y a d'itérations, plus le traitement est intéressant et intensif). Une de ces photos coûtera 50 roubles.

Dans la version HD, vous pouvez personnaliser le nombre d'itérations : 100 coûtera 50 roubles et 1 000 coûtera 250 roubles. Dans ce cas, l'image aura une résolution allant jusqu'à 1 200 pixels sur le côté le plus long et pourra être utilisée pour l'impression sur toile : Ostagram propose un tel service avec une livraison à partir de 1 800 roubles.

En février, les représentants d'Ostagram ont annoncé qu'ils n'accepteraient pas les demandes de traitement d'images des utilisateurs « des pays à capitalisme développé », mais l'accès au traitement de photos pour les utilisateurs de VKontakte du monde entier. À en juger par le code Ostagram publié sur GitHub, il a été développé par Sergey Morugin, un habitant de Nijni Novgorod âgé de 30 ans.

TJ a contacté le directeur commercial du projet, qui s'est présenté comme étant Andrey. Selon lui, Ostagram est apparu avant Instapainting, mais s'est inspiré d'un projet similaire appelé Vipart.

Ostagram a été développé par un groupe d’étudiants du NSTU. Alekseeva : après des premiers tests sur un groupe restreint d'amis, fin 2015, ils ont décidé de rendre le projet public. Au départ, le traitement de l’image était totalement gratuit et le plan était de gagner de l’argent en vendant des peintures imprimées. Selon Andrey, l'impression s'est avérée être le plus gros problème : les photos de personnes traitées par un réseau de neurones sont rarement agréables à l'œil humain, et le client final a besoin de beaucoup de temps pour ajuster le résultat avant de l'appliquer sur la toile, ce qui nécessite ressources machine importantes.

Les créateurs d'Ostagram voulaient utiliser les serveurs cloud d'Amazon pour traiter les images, mais après un afflux d'utilisateurs, il est devenu évident que les coûts dépasseraient mille dollars par jour avec un retour sur investissement minimal. Andrey, qui est également un investisseur dans le projet, a loué des capacités de serveur à Nijni Novgorod.

L'audience du projet est d'environ un millier de personnes par jour, mais certains jours, elle a atteint 40 000 personnes en raison des transitions de médias étrangers, qui avait déjà remarqué le projet avant les projets nationaux (Ostagram a même réussi à collaborer avec des DJ européens). La nuit, lorsque le trafic est faible, le traitement de l'image peut prendre 5 minutes, et le jour, jusqu'à une heure.

Si auparavant l'accès au traitement d'images était délibérément limité aux utilisateurs étrangers (ils pensaient commencer la monétisation en Russie), Ostagram compte désormais davantage sur un public occidental.

Aujourd’hui, les perspectives de récupération sont conditionnelles. Si chaque utilisateur payait 10 roubles pour le traitement, cela serait peut-être payant. […]

Il est très difficile de monétiser dans notre pays : nos citoyens sont prêts à attendre une semaine, mais ne paieront pas un centime pour cela. Les Européens y sont plus favorables - en termes de paiement pour accélérer et améliorer la qualité - et ciblent donc ce marché.

Andreï, représentant d'Ostagram

Selon Andreï, l'équipe d'Ostagram travaille sur nouvelle version site fortement axé sur la socialité : « Ce sera similaire à un service bien connu, mais que faire. » Les représentants de Facebook en Russie étaient déjà intéressés par le projet, mais les négociations sur la vente n'ont pas encore atteint le point de vente.

Exemples de travaux de service

Dans le flux du site Ostagram, vous pouvez également voir la combinaison d'images qui a abouti aux photos finales : c'est souvent encore plus intéressant que le résultat lui-même. Dans ce cas, les filtres - les images utilisées comme effet pour le traitement - peuvent être enregistrés pour une utilisation ultérieure.

Salutations, Habr! Vous avez probablement remarqué que le sujet du style des photographies pour les adapter à différents styles artistiques est activement discuté sur vos Internets. En lisant tous ces articles populaires, vous pourriez penser qu’il y a de la magie sous le capot de ces applications, et que le réseau neuronal imagine et redessine réellement l’image à partir de zéro. Il se trouve que notre équipe a été confrontée à une tâche similaire : dans le cadre d'un hackathon interne à l'entreprise, nous avons réalisé une stylisation vidéo, car... Il existait déjà une application pour les photos. Dans cet article, nous découvrirons comment le réseau « redessine » les images et nous analyserons les articles qui ont rendu cela possible. Je vous recommande de lire le post précédent avant de lire ce matériel et, en général, les bases des réseaux de neurones convolutifs. Vous y trouverez quelques formules, du code (je vais donner des exemples sur Theano et Lasagne), et aussi beaucoup d'images. Cet article est basé sur ordre chronologique l'apparition des articles et, par conséquent, les idées elles-mêmes. Parfois, je le diluerai avec notre expérience récente. Voici un garçon de l'enfer pour attirer votre attention.


Visualiser et comprendre les réseaux convolutifs (28 novembre 2013)

Tout d'abord, il convient de mentionner un article dans lequel les auteurs ont pu montrer qu'un réseau de neurones n'est pas une boîte noire, mais une chose tout à fait interprétable (d'ailleurs, aujourd'hui, cela peut être dit non seulement des réseaux convolutifs pour ordinateurs vision). Les auteurs ont décidé d'apprendre à interpréter les activations des neurones dans les couches cachées ; pour cela, ils ont utilisé un réseau neuronal déconvolutif (deconvnet), proposé plusieurs années plus tôt (d'ailleurs par les mêmes Seiler et Fergus, qui sont les auteurs de ce document). publication). Un réseau de déconvolution est en fait le même réseau avec des convolutions et des poolings, mais appliqué dans l'ordre inverse. Le travail original sur deconvnet utilisait le réseau dans un mode d'apprentissage non supervisé pour générer des images. Cette fois, les auteurs l’ont utilisé simplement pour revenir en arrière des caractéristiques obtenues après un passage à travers le réseau jusqu’à l’image originale. Le résultat est une image qui peut être interprétée comme le signal qui a provoqué cette activation dans les neurones. Naturellement, la question se pose : comment faire un passage inverse par convolution et non-linéarité ? Et plus encore grâce au max-pooling, il ne s’agit certainement pas d’une opération inversible. Examinons les trois composants.

ReLu inversé

Dans les réseaux convolutifs, la fonction d'activation est souvent utilisée ReLu(x) = max(0,x), ce qui rend toutes les activations sur le calque non négatives. Ainsi, lorsqu'on remonte dans la non-linéarité, il faut également obtenir des résultats non négatifs. Pour cela, les auteurs suggèrent d'utiliser le même ReLu. D'un point de vue architectural, Theano doit remplacer la fonction de gradient d'opération (le cahier infiniment précieux se trouve dans Lasagna Recipes, à partir de là, vous obtiendrez les détails de ce qu'est la classe ModifiedBackprop).

Class ZeilerBackprop(ModifiedBackprop): def grad(self, inputs, out_grads): (inp,) = inputs (grd,) = out_grads #return (grd * (grd > 0).astype(inp.dtype),) # rectifier explicitement return (self.nonlinearity(grd),) # utilise la non-linéarité donnée

Convolution inverse

C'est un peu plus compliqué, mais tout est logique : il suffit d'appliquer une version transposée du même noyau de convolution, mais aux sorties du ReLu inverse au lieu de la couche précédente utilisée dans la passe avant. Mais j'ai bien peur que ce ne soit pas si évident en mots, regardons la visualisation de cette procédure (vous trouverez encore plus de visualisations de circonvolutions).


Convolution avec foulée=1

Convolution avec foulée=1 Version inversée

Convolution avec foulée=2

Convolution avec foulée=2 Version inversée

Mise en commun inversée

Cette opération (contrairement aux précédentes) n'est généralement pas inversible. Mais nous aimerions quand même en quelque sorte franchir le maximum lors du passage retour. Pour ce faire, les auteurs suggèrent d'utiliser une carte indiquant où se trouvait le maximum lors d'un passage direct (changements d'emplacement maximum). Lors du passage inverse, le signal d'entrée est converti en dégroupage de manière à préserver approximativement la structure du signal d'origine ; ici, il est vraiment plus facile de voir que de décrire ;



Résultat

L'algorithme de visualisation est extrêmement simple :

  1. Faites une passe droite.
  2. Sélectionnez le calque qui nous intéresse.
  3. Enregistrez l'activation d'un ou plusieurs neurones et réinitialisez le reste.
  4. Tirez la conclusion inverse.

Chaque carré gris de l'image ci-dessous correspond à une visualisation du filtre (qui sert à la convolution) ou aux poids d'un neurone, et chaque image en couleur- c'est la partie de l'image originale qui active le neurone correspondant. Pour plus de clarté, les neurones d'une même couche sont regroupés en groupes thématiques. En général, il s'est soudainement avéré que le réseau neuronal apprend exactement ce que Hubel et Weisel ont écrit dans leurs travaux sur la structure du système visuel, pour lesquels ils ont été récompensés. Prix ​​Nobel en 1981. Grâce à cet article, nous avons obtenu une représentation visuelle de ce qu'un réseau de neurones convolutifs apprend dans chaque couche. C'est cette connaissance qui nous permettra plus tard de manipuler le contenu de l'image générée, mais c'est encore loin ; les années suivantes furent consacrées à l'amélioration des méthodes de « trépanation » des réseaux de neurones. De plus, les auteurs de l'article ont proposé une méthode pour analyser la meilleure façon de construire une architecture de réseau neuronal convolutif pour atteindre meilleurs résultats(bien qu’ils n’aient pas gagné ImageNet 2013, mais ils ont atteint le sommet ; MISE À JOUR: il s'avère qu'ils ont gagné, Clarifai est ce qu'ils sont).


Visualisation des fonctionnalités


Voici un exemple de visualisation d'activations à l'aide de deconvnet, aujourd'hui ce résultat semble médiocre, mais c'était alors une percée.


Cartes de saillance utilisant deconvnet

Réseaux convolutifs profonds : visualisation de modèles de classification d'images et de cartes de saillance (19 avril 2014)

Cet article est consacré à l'étude des méthodes de visualisation des connaissances contenues dans un réseau de neurones convolutifs. Les auteurs proposent deux méthodes de visualisation basées sur la descente de gradient.

Visualisation du modèle de classe

Imaginez donc que nous disposions d’un réseau de neurones entraîné pour résoudre un problème de classification en un certain nombre de classes. Notons la valeur d'activation du neurone de sortie, qui correspond à la classe c. Alors le problème d’optimisation suivant nous donne exactement l’image qui maximise la classe sélectionnée :



Ce problème peut être facilement résolu en utilisant Theano. Habituellement, nous demandons au framework de prendre la dérivée par rapport aux paramètres du modèle, mais cette fois nous supposons que les paramètres sont fixes et que la dérivée est prise par rapport à l'image d'entrée. La fonction suivante sélectionne la valeur maximale de la couche de sortie et renvoie une fonction qui calcule la dérivée de l'image d'entrée.


def compile_saliency_function(net): """ Compile une fonction pour calculer les cartes de saillance et les classes prédites pour un mini-lot donné d'images d'entrée. """ inp = net["input"].input_var outp = lasagne.layers.get_output(net ["fc8"], déterministe=Vrai) max_outp = T.max(outp, axis=1) saillance = theano.grad(max_outp.sum(), wrt=inp) max_class = T.argmax(outp, axis=1) retourner theano.function(, )

Vous avez probablement vu d'étranges images avec des têtes de chiens sur Internet - DeepDream. Dans l'article original, les auteurs utilisent le processus suivant pour générer des images qui maximisent la classe sélectionnée :

  1. Initialisez l'image initiale avec des zéros.
  2. Calculez la valeur dérivée de cette image.
  3. Modifiez l'image en y ajoutant l'image résultante du dérivé.
  4. Revenez au point 2 ou quittez la boucle.

Les images résultantes sont :




Et si on initialise la première image vraie photo et démarrer le même processus ? Mais à chaque itération, nous sélectionnerons une classe aléatoire, réinitialiserons le reste et calculerons la valeur de la dérivée, nous obtiendrons alors quelque chose comme ce rêve profond.


Attention 60 Mo


Pourquoi y a-t-il tant de visages et d'yeux de chiens ? C'est simple : il y a près de 200 chiens sur 1000 classes dans imagenet, ils ont des yeux. Et aussi de nombreuses classes où il y a simplement du monde.

Extraction de l'importance de la classe

Si ce processus est initialisé avec une photographie réelle, arrêté après la première itération et que la valeur de la dérivée est dessinée, alors nous obtiendrons une telle image, en ajoutant laquelle à l'originale, nous augmenterons la valeur d'activation de la classe sélectionnée.


Cartes de saillance utilisant un dérivé


Encore une fois, le résultat est « couci-couça ». Il est important de noter que cela nouvelle façon visualisation des activations (rien n'empêche de fixer les valeurs des activations non pas sur la dernière couche, mais en général sur n'importe quelle couche du réseau et de prendre la dérivée par rapport à l'image d'entrée). Le prochain article combinera les deux approches précédentes et nous donnera un outil sur la façon de configurer le transfert de style, qui sera décrit plus tard.

En quête de simplicité : le réseau entièrement convolutif (13 avril 2015)

Cet article ne porte généralement pas sur la visualisation, mais sur le fait que remplacer le pooling par une convolution avec une grande foulée n'entraîne pas de perte de qualité. Mais comme résultat de leurs recherches, les auteurs ont proposé une nouvelle façon de visualiser les caractéristiques, qu’ils ont utilisée pour analyser plus précisément ce que le modèle apprend. Leur idée est la suivante : si nous prenons simplement la dérivée, alors lors de la déconvolution, les caractéristiques qui étaient inférieures à zéro dans l'image d'entrée ne sont pas renvoyées (en utilisant ReLu pour l'image d'entrée). Et cela conduit à l’apparition de valeurs négatives. D'un autre côté, si vous utilisez deconvnet, alors un autre ReLu est extrait du dérivé de ReLu - cela vous permet de ne pas renvoyer de valeurs négatives, mais comme vous l'avez vu, le résultat est « couci-couça ». Mais et si vous combiniez ces deux méthodes ?




class GuidedBackprop(ModifiedBackprop) : def grad(self, inputs, out_grads) : (inp,) = inputs(grd,) = out_grads dtype = inp.dtype return (grd * (inp > 0).astype(dtype) * (grd > 0).astype(dtype),)

Vous obtiendrez alors une image complètement nette et interprétable.


Cartes de saillance utilisant Rétropropagation guidée

Allez plus loin

Maintenant, réfléchissons à ce que cela nous donne ? Je vous rappelle que chaque couche convolutive est une fonction qui reçoit un tenseur tridimensionnel en entrée et produit également un tenseur tridimensionnel en sortie, peut-être d'une dimension différente d x w x h; d la profondeur est le nombre de neurones dans la couche, chacun d'eux génère une carte caractéristique de taille w je suis x h huit.


Essayons l'expérience suivante sur le réseau VGG-19 :



conv1_2

Oui, on ne voit presque rien, parce que... la zone de réception est très petite, c'est la deuxième convolution de 3x3, respectivement, la surface totale est de 5x5. Mais en zoomant, nous voyons que la fonctionnalité n’est qu’un détecteur de gradient.




conv3_3


conv4_3


conv5_3


piscine5


Imaginons maintenant qu'au lieu du maximum sur le bloc, nous prenons la dérivée de la valeur de la somme de tous les éléments du bloc sur l'image d'entrée. Alors évidemment, la zone réceptrice d’un groupe de neurones couvrira toute l’image d’entrée. Pour les premières couches, nous verrons des cartes lumineuses, à partir desquelles nous conclurons qu'il s'agit de détecteurs de couleurs, puis de dégradés, puis de bords, et ainsi de suite vers des motifs plus complexes. Plus le calque est profond, plus l’image est sombre. Cela s'explique par le fait que les couches plus profondes ont un motif plus complexe qu'elles détectent, et qu'un motif complexe apparaît moins souvent qu'un motif simple, de sorte que la carte d'activation s'estompe. La première méthode convient à la compréhension des couches avec des motifs complexes, et la seconde est réservée aux couches simples.


conv1_1


conv2_2


conv4_3


Vous pouvez télécharger une base de données plus complète d'activations pour plusieurs images et .

Un algorithme neuronal du style artistique (2 septembre 2015)

Ainsi, quelques années se sont écoulées depuis la première trépanation réussie d'un réseau neuronal. Nous (au sens de l'humanité) avons entre les mains outil puissant, ce qui nous permet de comprendre ce que le réseau neuronal apprend, et également de supprimer ce que nous ne voulons pas vraiment qu’il apprenne. Les auteurs de cet article développent une méthode qui permet à une image de générer une carte d'activation similaire à une image cible, et peut-être même plusieurs - c'est la base de la stylisation. Nous appliquons du bruit blanc à l'entrée et, en utilisant un processus itératif similaire à celui du rêve profond, nous réduisons cette image à une image dont les cartes de caractéristiques sont similaires à l'image cible.

Perte de contenu

Comme déjà mentionné, chaque couche du réseau neuronal produit un tenseur tridimensionnel d'une certaine dimension.




Notons la sortie jeème couche de l'entrée comme . Ensuite, si nous minimisons la somme pondérée des résidus entre l'image d'entrée et une image que nous visons c, alors vous obtiendrez exactement ce dont vous avez besoin. Peut être.



Pour expérimenter cet article, vous pouvez utiliser cet ordinateur portable magique, les calculs s'y déroulent (aussi bien sur le GPU que sur le CPU). Le GPU est utilisé pour calculer les caractéristiques du réseau neuronal et la valeur de la fonction de coût. Theano produit une fonction capable de calculer le gradient de la fonction objectif eval_grad par image d'entrée x. Ceci est ensuite introduit dans lbfgs et le processus itératif commence.


# Initialiser avec une image de bruit generate_image.set_value(floatX(np.random.uniform(-128, 128, (1, 3, IMAGE_W, IMAGE_W)))) x0 = generate_image.get_value().astype("float64") xs = xs.append(x0) # Optimiser, en enregistrant périodiquement le résultat pour i dans range(8) : print(i) scipy.optimize.fmin_l_bfgs_b(eval_loss, x0.flatten(), fprime=eval_grad, maxfun=40) x0 = generate_image.get_value().astype("float64") xs.append(x0)

Si nous exécutons l'optimisation d'une telle fonction, nous obtiendrons rapidement une image similaire à celle cible. Nous pouvons désormais utiliser le bruit blanc pour recréer des images similaires à certaines images de contenu.


Perte de contenu : conv4_2



Processus d'optimisation




Il est facile de remarquer deux caractéristiques de l’image résultante :

  • les couleurs sont perdues - c'est le résultat du fait que dans exemple spécifique seule la couche conv4_2 a été utilisée (ou, en d'autres termes, le poids w pour elle était non nul, et pour les autres couches il était nul) ; comme vous vous en souvenez, ce sont les premiers calques qui contiennent des informations sur les couleurs et les transitions de dégradé, et les derniers contiennent des informations sur des détails plus importants, ce que nous observons : les couleurs sont perdues, mais pas le contenu ;
  • certaines maisons ont « bougé », c'est-à-dire les lignes droites sont légèrement courbées - en effet, plus la couche est profonde, plus moins d'informations il contient des informations sur la position spatiale de l'entité (résultat de l'utilisation de convolutions et de pooling).

L’ajout de premières couches corrige immédiatement la situation des couleurs.


Perte de contenu : conv1_1, conv2_1, conv4_2


J'espère que vous avez maintenant l'impression d'avoir un certain contrôle sur ce qui est redessiné sur l'image du bruit blanc.

Perte de style

Et maintenant, passons à la partie la plus intéressante : comment pouvons-nous transmettre le style ? Qu'est-ce que le style ? Évidemment, le style n'est pas quelque chose que nous avons optimisé dans Content Loss, car il contient beaucoup d'informations sur les positions spatiales des entités. La première chose que nous devons faire est donc de supprimer d'une manière ou d'une autre ces informations des vues reçues sur chaque couche.


L'auteur suggère la méthode suivante. Prenons le tenseur à la sortie d'une certaine couche, développons-le le long des coordonnées spatiales et calculons la matrice de covariance entre les matrices. Notons cette transformation par G. Qu'avons-nous réellement fait ? Nous pouvons dire que nous avons calculé la fréquence à laquelle les caractéristiques d'un patch apparaissent par paires ou, en d'autres termes, nous avons approximé la distribution des fonctionnalités dans les patchs avec une distribution normale multivariée.




Ensuite, Style Loss est entré comme suit, où s- voici une image avec du style :



On essaie pour Vincent ? Nous obtenons, en principe, quelque chose d'attendu - du bruit à la manière de Van Gogh, les informations sur la disposition spatiale des caractéristiques sont complètement perdues.


Vincent




Et si vous mettiez une photo à la place d'une image de style ? Vous obtiendrez des caractéristiques familières, des couleurs familières, mais la position spatiale est complètement perdue.


Photo avec perte de style


Vous vous êtes probablement demandé pourquoi on calcule la matrice de covariance et pas autre chose ? Après tout, il existe de nombreuses façons d’agréger des entités de manière à perdre les coordonnées spatiales. C’est vraiment une question ouverte, et si l’on prend quelque chose de très simple, le résultat ne changera pas radicalement. Vérifions cela, nous ne calculerons pas la matrice de covariance, mais simplement la valeur moyenne de chaque plaque.




perte de style simple

Perte combinée

Il existe bien entendu une volonté de mélanger ces deux fonctions de coût. Ensuite, nous générerons une image à partir du bruit blanc de telle sorte qu'elle conservera les caractéristiques de l'image de contenu (qui sont liées aux coordonnées spatiales), et contiendra également des caractéristiques de « style » qui ne sont pas liées aux coordonnées spatiales, c'est-à-dire nous espérons que les détails de l'image du contenu resteront intacts à leur place, mais seront redessinés avec le style souhaité.



En fait, il existe également un régulariseur, mais nous l'omettrons par souci de simplicité. Reste à répondre à la question suivante : quelles couches (poids) faut-il utiliser lors de l'optimisation ? Et je crains de ne pas avoir de réponse à cette question, et les auteurs de l’article non plus. Ils ont une proposition d'utiliser ce qui suit, mais cela ne signifie pas du tout qu'une autre combinaison fonctionnera moins bien, l'espace de recherche est trop grand. Seule règle qui découle de la compréhension du modèle : cela ne sert à rien de prendre des couches adjacentes, car leurs caractéristiques ne différeront pas beaucoup les unes des autres, donc une couche de chaque groupe conv*_1 est ajoutée au style.


# Définir la fonction de perte loss = # perte de contenu loss.append(0.001 * content_loss(photo_features, gen_features, "conv4_2")) # perte de style loss.append(0.2e6 * style_loss(art_features, gen_features, "conv1_1")) loss.append (0.2e6 * style_loss(art_features, gen_features, "conv2_1")) pertes.append(0.2e6 * style_loss(art_features, gen_features, "conv3_1")) pertes.append(0.2e6 * style_loss(art_features, gen_features, "conv4_1") ) loss.append(0.2e6 * style_loss(art_features, gen_features, "conv5_1")) # pénalité de variation totale loss.append(0.1e-7 * total_variation_loss(generated_image)) total_loss = sum(losses)

Le modèle final peut être présenté comme suit.




Et voici le résultat des maisons avec Van Gogh.



Essayer de contrôler le processus

Rappelons-nous les parties précédentes, déjà deux ans avant l'article actuel, d'autres scientifiques recherchaient ce qu'apprend réellement un réseau de neurones. Armé de tous ces articles, vous pouvez générer des visualisations de fonctionnalités différents styles, diverses images, différentes résolutions et tailles, et essayez de comprendre quelles couches prendre avec quel poids. Mais même une nouvelle pesée des couches ne donne pas un contrôle total sur ce qui se passe. Le problème ici est plus conceptuel : nous optimisons la mauvaise fonction! Comment ça, demandez-vous ? La réponse est simple : cette fonction minimise l'écart... eh bien, vous voyez l'idée. Mais ce que nous voulons vraiment, c’est que l’image nous plaise. La combinaison convexe des fonctions de perte de contenu et de style n’est pas une mesure de ce que notre esprit considère comme beau. Il a été remarqué que si vous continuez la stylisation trop longtemps, la fonction de coût diminue naturellement de plus en plus, mais la beauté esthétique du résultat diminue fortement.




Bon, d'accord, il y a encore un problème. Disons que nous avons trouvé une couche qui extrait les fonctionnalités dont nous avons besoin. Disons que certaines textures sont triangulaires. Mais ce calque contient également de nombreuses autres caractéristiques, telles que des cercles, que nous ne souhaitons vraiment pas voir dans l’image résultante. D'une manière générale, si nous pouvions embaucher un million de Chinois, nous pourrions visualiser toutes les caractéristiques d'une image de style et, par la force brute, simplement marquer celles dont nous avons besoin et les inclure uniquement dans la fonction de coût. Mais pour des raisons évidentes, ce n’est pas si simple. Mais que se passe-t-il si nous supprimons simplement de l'image de style tous les cercles que nous ne voulons pas voir dans le résultat ? Ensuite, l'activation des neurones correspondants qui répondent aux cercles ne fonctionnera tout simplement pas. Et bien sûr, cela n’apparaîtra pas dans l’image résultante. C'est la même chose avec les fleurs. Imaginez une image lumineuse avec beaucoup de couleurs. La répartition des couleurs sera très floue dans tout l'espace et la répartition de l'image résultante sera la même, mais lors du processus d'optimisation, les pics qui se trouvaient sur l'original seront probablement perdus. Il s'est avéré que la simple réduction de la profondeur de bits de la palette de couleurs résout ce problème. La densité de distribution de la plupart des couleurs sera proche de zéro et il y aura des pics importants dans quelques zones. Ainsi, en manipulant l'original dans Photoshop, nous manipulons les caractéristiques extraites de l'image. Il est plus facile pour une personne d'exprimer visuellement ses désirs que d'essayer de les formuler dans le langage mathématique. Au revoir. En conséquence, les concepteurs et les gestionnaires, armés de Photoshop et de scripts pour visualiser les fonctionnalités, ont obtenu des résultats trois fois plus rapidement que les mathématiciens et les programmeurs.


Un exemple de manipulation de la couleur et de la taille des entités


Ou vous pouvez utiliser une simple image comme style



Résultats








Voici une vidéo, mais seulement avec la bonne texture

Réseaux de textures : synthèse feed-forward de textures et d'images stylisées (10 mars 2016)

Il semble que l’on pourrait s’arrêter là, ne serait-ce qu’à une nuance. L’algorithme de stylisation ci-dessus prend beaucoup de temps. Si nous prenons une implémentation dans laquelle lbfgs s'exécute sur le processeur, le processus prend environ cinq minutes. Si vous le réécrivez pour que l'optimisation aille au GPU, le processus prendra 10 à 15 secondes. Ce n'est pas bon. Peut-être que les auteurs de cet article et du suivant ont pensé à la même chose. Les deux publications ont été publiées indépendamment, à 17 jours d’intervalle, soit près d’un an après l’article précédent. Les auteurs de l'article actuel, comme les auteurs du précédent, se sont occupés de générer des textures (si vous réinitialisez simplement la perte de style à zéro, c'est ce que vous obtiendrez). Ils ont proposé d'optimiser non pas une image obtenue à partir du bruit blanc, mais un réseau de neurones qui génère une image stylisée.




Désormais, si le processus de style n’inclut aucune optimisation, il vous suffit d’effectuer une passe avant. Et l'optimisation n'est nécessaire qu'une seule fois pour former le réseau de générateurs. Cet article utilise un générateur hiérarchique, où chaque prochain z plus grand en taille que le précédent et échantillonné à partir du bruit dans le cas de la génération de texture, et à partir d'une base de données d'images pour la formation du styliste. Il est essentiel d'utiliser autre chose que la partie formation d'imagenet, car... les fonctionnalités à l'intérieur du réseau de perte sont calculées par le réseau formé pendant la partie formation.



Pertes de perception pour le transfert de style en temps réel et la super-résolution (27 mars 2016)

Comme le titre l'indique, les auteurs, qui n'avaient que 17 jours de retard avec l'idée d'un réseau génératif, travaillaient à augmenter la résolution des images. Ils se sont apparemment inspirés des succès de l'apprentissage résiduel sur le dernier imagenet.




En conséquence, bloc résiduel et bloc de conv.



Ainsi, nous disposons désormais, en plus du contrôle du style, d'un générateur rapide (grâce à ces deux articles, le temps de génération d'une image se mesure en dizaines de ms).

Fin

Nous avons utilisé les informations des articles examinés et le code des auteurs comme point de départ pour créer une autre application de style de la première application de style vidéo :



Génère quelque chose comme ça.