20220116のTensorFlowに関する記事は1件です。

類似画像検索 お試しkeras編

kerasによる類似画像検索の実装。 まず、類似画像検索とは。 画像から画像を探すことであり、これはCNN等にて作成したモデルを応用して可能である。 類似画像検索のおもしろいのは、学習済モデルの全結合層を用いて実装する形となっている。 VGG19のモデルを以下に記載する。 上記の場合、使用するのは、fc2(Dense)層の値を使用する。 さて、kerasを使用した簡単な実装を記載します。 ①VGG19の重みダウンロード wget https://github.com/fchollet/deep-learning-models/releases/download/v0.1/vgg19_weights_tf_dim_ordering_tf_kernels.h5 ※以降ではvgg19.h5にリネームしています. ②検索対象の作成 類似画像の検索となるため、検索対象を作成します。 自身で画像を持っていれば特定のフォルダにまとめてください。 スレイピング等でも可能ですが、最近は制限が増えているため対象サイトがスクレイピング可能か確認下さい. ③プログラム 今回はQiitaで公開されていたプログラムを一部変更して使用させてもらっています。 誰でも使用できるように、検索対象とターゲット画像をGUIにて操作可能となっていました。 main.py import glob from pathlib import Path import tkinter import tkinter.filedialog #License #The MIT License import keras from keras.models import Model from keras.layers import Input, Dense from keras.preprocessing import image from keras.applications.vgg19 import preprocess_input from keras.models import load_model #License #These weights are ported from the ones released by VGG at Oxford under the Creative Commons Attribution License. #https://keras.io/applications/ from keras.applications.vgg19 import VGG19, preprocess_input #Apache License Version 2.0 #https://github.com/nmslib/nmslib/blob/master/README.md import nmslib #https://numpy.org/license.html import numpy as np current_path = Path.cwd() # refer https://qiita.com/wasnot/items/20c4f30a529ae3ed5f52 # refer https://qiita.com/K-jun/items/cab923d49a939a8486fc def main(): print("データベースを選択してください") print("サブディレクトリ内の画像もすべて検索対象となります") data_folder_path = tkinter.filedialog.askdirectory(initialdir = current_path, title = 'choose data folder') print("データベースと比較したい画像を選択してください") test_img_path = tkinter.filedialog.askopenfilename(initialdir = current_path, #title = 'choose test image', filetypes = [('image file', '*.jpeg;*.jpg;*.png')]) title = 'choose test image', filetypes = [('image file', '*')]) #base_model = VGG19(weights="imagenet") base_model = VGG19(weights="vgg19.h5") #base_model.summary() #outputsを"fc2"と指定し、2番目の全結合層を出力します model = Model(inputs=base_model.input, outputs=base_model.get_layer("fc2").output) test_img = image.load_img(test_img_path, target_size=(224, 224)) x = image.img_to_array(test_img) x = np.expand_dims(x, axis=0) x = preprocess_input(x) test_fc2_features = model.predict(x) #選択したフォルダに存在するpng,jpeg,jpgをサブディレクトリも含めて抽出 png_list = glob.glob(data_folder_path + "/**/*.png", recursive=True) jpeg_list = glob.glob(data_folder_path + "/**/*.jpeg", recursive=True) jpg_list = glob.glob(data_folder_path + "/**/*.jpg", recursive=True) image_list = png_list + jpeg_list + jpg_list fc2_list = [] for image_path in image_list: img = image.load_img(image_path, target_size=(224, 224)) x = image.img_to_array(img) x = np.expand_dims(x, axis=0) x = preprocess_input(x) fc2_features = model.predict(x) fc2_list.append(fc2_features[0]) index = nmslib.init(method='hnsw', space='cosinesimil') index.addDataPointBatch(fc2_list) index.createIndex({'post': 2}, print_progress=True) ids, distances = index.knnQuery(test_fc2_features, k=len(image_list)) result = [image_list[i] for i in ids] #print(ids) #print(distances) #print(result) count = 0 print("選択した画像は " , test_img_path, " です") print("選択した画像に似ている順に表示します") for i, id in enumerate(ids): print(image_list[id], " : 距離: ", distances[i]) count += 1 if count == 5: break main() ④実行結果 結果は、検索対象の画像から類似している上位5つを表示するようにしています。 ****************************************************選択した画像は /home/taroimo/2022/similary/Target/sea.jpg です 選択した画像に似ている順に表示します /home/konosuke/2022/similary/DB/DSC00493.jpg : 距離: 0.49756563 /home/konosuke/2022/similary/DB/PXL_20211015_043202997.jpg : 距離: 0.54518986 /home/konosuke/2022/similary/DB/DSC02634.jpg : 距離: 0.5474366 /home/konosuke/2022/similary/DB/DSC00424.jpg : 距離: 0.5517075 /home/konosuke/2022/similary/DB/PXL_20211014_003302316.jpg : 距離: 0.5669149 以上で、実装終了です。 あまり頭を使わずに類似画像検索を検証できてよかったです。 実際に特定の目的で使用する場合の作成方法を今後は模索しようと思います。 参考サイト
  • このエントリーをはてなブックマークに追加
  • Qiitaで続きを読む