Deux fois avant (1/3): https://qiita.com/tfull_tf/items/6015bee4af7d48176736 Dernière fois (2/3): https://qiita.com/tfull_tf/items/968bdb8f24f80d57617e
Code entier: https://github.com/tfull/character_recognition
Maintenant que le modèle de reconnaissance kana a atteint un niveau où il est possible de vérifier le fonctionnement du système, nous allons générer une image avec l'interface graphique, la charger dans le modèle et générer des caractères.
J'utiliserai Tkinter, alors installez-le.
# Mac +Pour Homebrew
$ brew install tcl-tk
#Pour Ubuntu Linux
$ sudo apt install python-tk
Créez un canevas et faites un clic gauche pour dessiner une ligne blanche et cliquez avec le bouton droit pour dessiner une ligne noire (en fait une gomme car c'est un fond noir). Préparez deux boutons, l'un qui reconnaît les caractères écrits et l'autre qui efface les caractères écrits (remplit en noir).
import tkinter
# from PIL import Image, ImageDraw
class Board:
def __init__(self):
self.image_size = 256
self.window = tkinter.Tk()
self.window.title("Entrée Kana")
self.frame = tkinter.Frame(self.window, width = self.image_size + 2, height = self.image_size + 40)
self.frame.pack()
self.canvas = tkinter.Canvas(self.frame, bg = "black", width = self.image_size, height = self.image_size)
self.canvas.place(x = 0, y = 0)
self.canvas.bind("<ButtonPress-1>", self.click_left)
self.canvas.bind("<B1-Motion>", self.drag_left)
self.canvas.bind("<ButtonPress-3>", self.click_right)
self.canvas.bind("<B3-Motion>", self.drag_right)
self.button_detect = tkinter.Button(self.frame, bg = "blue", fg = "white", text = "reconnaissance", width = 100, height = 40, command = self.press_detect)
self.button_detect.place(x = 0, y = self.image_size)
self.button_delete = tkinter.Button(self.frame, bg = "green", fg = "white", text = "Supprimer", width = 100, height = 40, command = self.press_delete)
self.button_delete.place(x = self.image_size // 2, y = self.image_size)
# self.image = Image.new("L", (self.image_size, self.image_size))
# self.draw = ImageDraw.Draw(self.image)
def press_detect(self):
output = recognize(np.array(self.image).reshape(1, 1, self.image_size, self.image_size)) #reconnaître est une fonction qui reconnaît l'utilisation de l'apprentissage automatique
sys.stdout.write(output)
sys.stdout.flush()
def press_delete(self):
# self.canvas.delete("all")
# self.draw.rectangle((0, 0, self.image_size, self.image_size), fill = 0)
def click_left(self, event):
ex = event.x
ey = event.y
self.canvas.create_oval(
ex, ey, ex, ey,
outline = "white",
width = 8
)
# self.draw.ellipse((ex - 4, ey - 4, ex + 4, ey + 4), fill = 255)
self.x = ex
self.y = ey
def drag_left(self, event):
ex = event.x
ey = event.y
self.canvas.create_line(
self.x, self.y, ex, ey,
fill = "white",
width = 8
)
# self.draw.line((self.x, self.y, ex, ey), fill = 255, width = 8)
self.x = ex
self.y = ey
def click_right(self, event):
ex = event.x
ey = event.y
self.canvas.create_oval(
ex, ey, ex, ey,
outline = "black",
width = 8
)
# self.draw.ellipse((ex - 4, ey - 4, ex + 4, ey + 4), fill = 0)
self.x = event.x
self.y = event.y
def drag_right(self, event):
ex = event.x
ey = event.y
self.canvas.create_line(
self.x, self.y, ex, ey,
fill = "black",
width = 8
)
# self.draw.line((self.x, self.y, ex, ey), fill = 0, width = 8)
self.x = event.x
self.y = event.y
Avec cela, vous pouvez écrire et effacer des caractères.
Après quelques recherches, Tkinter's Canvas peut tracer des lignes, donc il peut être écrit, mais il semble qu'il n'est pas possible de lire ce que vous avez écrit et de le quantifier.
Alors que je cherchais une solution, j'ai trouvé un argument selon lequel je devrais avoir Pillow en interne et dessiner la même chose sur Pillow's Image lorsque je dessinais sur Canvas. (Je ne pouvais pas penser à cela, alors j'ai pensé que c'était une idée très intelligente.) La partie commentée dans le code ci-dessus correspond à cela. L'image de Pillow peut être rapidement transformée en un tableau numpy avec numpy.array, ce qui facilite l'intégration d'un modèle d'apprentissage automatique.
Une interface graphique pour la saisie de caractères manuscrits et un modèle d'apprentissage automatique pour classer les images kana ont été achevés. Ce qui suit est une combinaison de ceux-ci.
YouTube: https://www.youtube.com/watch?v=a0MBfVVp7mA
Ce n'est pas très précis, mais il l'a reconnu assez correctement. Il ne reconnaît pas les caractères sales, mais lorsque j'ai tapé «aiueo» avec soin, il affiche correctement les caractères correspondants.
J'ai essayé le "Hello", si le "blood" est reconnu dans le "La" et la "filtration" était fréquente. J'étais curieux, alors quand j'ai vérifié les données d'image de "Chi", j'ai trouvé qu'il y avait une légère différence entre la forme de "Chi" que j'ai écrite et celle de l'image. Depuis que je n'ai appris que 3 types de polices, il semble que je ne puisse pas gérer l'entrée avec des formes étranges. Lorsque j'ai écrit les caractères sous une forme proche des données d'entrée, ils l'ont correctement reconnu.
Le temps de reconnaissance produit le résultat en un instant sans utiliser le GPU pour le modèle d'apprentissage automatique.
Ce serait idéal si nous pouvions reconnaître les kanji, mais les destinations de classement sont de 169 à des milliers. Kana seul n'est pas assez précis, donc je pense que les performances sont susceptibles de chuter immédiatement.
Cela prendra du temps, mais je pense que ce sera plus pratique comme interface si vous sortez les n premiers éléments avec une forte probabilité de classification.
Après cela, si vous apprenez la certitude en tant que mot et que vous la reconnaissez à la forme du caractère + la probabilité en tant que mot, la précision lors de la saisie d'un mot ou d'une phrase significative peut augmenter. (Par exemple, lorsque vous entrez "bonjour", ajoutez que "ha" est sur le point de venir.)
Recommended Posts