【Python】同じような画像が色々な組み合わせで存在する場合に重複分を削除するスクリプトを作った話
773 語
4 分
【Python】同じような画像が色々な組み合わせで存在する場合に重複分を削除するスクリプトを作った話
はじまり

135ml
あー、そういえば、重複した同じような画像が色々な組み合わせで出てきた際に、一気に削除してくれるスクリプトを作ったのを思い出したわ。今回はそれを紹介するぜ。

リサちゃん
急だな
ツールの紹介
起動する関数は、RemoveDuplication()です。

今回重複を削除するファイルはこれらの画像になります。

スクリプトを起動して、それらの画像があるフォルダを選択します。

まず、削除する前に「Assessment」モードを選択します。

評価方法を選びます。「PixelMatch」を使います。

すると、画像の重複がどれぐらいあるのかをテキストファイルに吐き出します。
今回、Assessmentで調査した結果のテキストファイルから、前の画像と0.87の割合でピクセルが合致していたら、その画像を削除することにします。

再度、スクリプトを起動して、「Remove」モードにして「PixelMatch」モードを選択して、「87」(=0.87)を入力します。

削除処理が完了しました!(ちょっとデバッグしながらお届けしてます・・・。)

左が削除する前にバックアップしておいたもので、右が実際に削除したものです。
87%以上合致している画像は削除されています。

スクリプトの紹介
こちらがスクリプトになります。
def RemoveDuplication(folderList): ''' folderList : List String absolutely path, of file filtered with extension in the selected folder. extracted_dir : String absolutely path of directory has selected file match_rate : Float rate border_line : border line ''' if len(folderList) == 0: print('\nImageEditor exits because of no target files.') sys.exit(0)
extracted_dir = os.path.dirname(folderList[0])
# Error Handling if InputController.CheckWhetherSjisExists([folderList[0], extracted_dir], __file__) == True: sys.exit(0)
# Decide to remove or don't executeMode = InputController.RepeatInputWithMultiChoices('\nYou wanna Remove or Assessment overlapped images? (R/A)', ['R', 'A'])
assessMode = 'N' border_line = 70 listForText = [] # compare both image to remove img1 or not for i in range(0, len(folderList) - 1): imgName1 = os.path.splitext(os.path.basename(folderList[i]))[0] imgName2 = os.path.splitext(os.path.basename(folderList[i+1]))[0] # Decide method of assessment while assessMode != 'F' and assessMode != 'P': assessMode = InputController.RepeatInputWithMultiChoices('\nWhich method to assess?\n[ F: FeaturePoint, P: PixelMatch ] : ', ['F', 'P']) if executeMode == 'R': if assessMode == 'F': border_line = InputController.RepeatInputWithMultiChoices('How many matches are required not to remove? : ', [0, 100]) elif assessMode == 'P': border_line = InputController.RepeatInputWithMultiChoices('How many matches are required to remove? : ', [0, 100]) elif executeMode == 'S': pass # do assessment if assessMode == 'F': match_rate = JudgeMatchRateByFeaturePoint(folderList[i], folderList[i+1]) match_rate = int(match_rate * 100) print('degree of similarity between "{imgName1}" and "{imgName2}" is {rate}'.format(imgName1=imgName1,imgName2=imgName2,rate=match_rate)) elif assessMode == 'P': match_rate = JudgeMatchRateByPixelMatch(folderList[i], folderList[i+1]) match_rate = int(match_rate * 100) print('match rate between "{imgName1}" and "{imgName2}" is {rate}'.format(imgName1=imgName1,imgName2=imgName2,rate=match_rate)) listForText.append('"{imgName1}" and "{imgName2}" is {rate}'.format(imgName1=imgName1,imgName2=imgName2,rate=match_rate)) # Remove files if executeMode == 'R': if assessMode == 'F': if match_rate <= border_line: os.remove(folderList[i]) elif assessMode == 'P': if match_rate >= border_line: os.remove(folderList[i]) # write to .txt file TextEditor.WriteText(DirEditor.GenerateFileName(extracted_dir, sep, 'match_rate.txt'), listForText)
print('RemoveDuplication is terminated.\nCheck directory "{dirname}"'.format(dirname=extracted_dir))ざっと書くと、以下の2軸での処理をこの関数で記載しています。まあ、ぶっちゃけ「FeaturePoint」の評価方法はあまり使っていませんね・・・。名残で残しているだけです。
| モード | 評価方法「FeaturePoint」 | 評価方法「PixelMatch」 |
|---|---|---|
| Removeモード | R、F | R、P(今回はこれを使った) |
| Assessmentモード | A、F | A、P |
おしまい

135ml
以上、重複を削除するツールでした。以前に問題集が載っている動画を画像にしたことがあったけど、それと組み合わせると沢山ある同じ画像を減らせるってわけよ。

リサちゃん
スッキリしたな
このツールで重複を削除した後は・・・
この重複を除いた複数の画像を一気にトリミングしたい場合は、以下のツールで切り出してみてはいかがでしょうか? こちらもPythonで動きます!
【Python】複数の画像を一気にトリミングするスクリプトを作った話
複数の画像を一気にトリミングするツールをPythonで作りました。使い方としては、最初に切り出したい範囲を選んで確定したら、そのエリアで後続の画像も切り出します。利用したモジュールは、OpenCVやTkinter、matplotlibになります。
www.endorphinbath.com

ちなみにこのツールを使う前段としての記事が以下に載っています。よければ見てみて下さい。 こちらもPythonで動きます。
【Python】動画をフレームごとの画像にして出力するスクリプトを作った話
動画を画像として切り出すツールをPythonで作りました。OpenCVを利用しています。動画として視聴する必要がないコンテンツはこのツールで画像にしてしまいましょう!
www.endorphinbath.com

以上になります!
記事を共有
この記事が役に立ったなら、ぜひ他の人と共有してください!
【Python】同じような画像が色々な組み合わせで存在する場合に重複分を削除するスクリプトを作った話
https://endorphinbath.com/posts/remove-duplicate-images/ 関連記事 スマート
1
【Python】複数の画像を一気にトリミングするスクリプトを作った話
Code 複数の画像を一気にトリミングするツールをPythonで作りました。使い方としては、最初に切り出したい範囲を選んで確定したら、そのエリアで後続の画像も切り出します。利用したモジュールは、OpenCVやTKinter、matplotlibになります。
2
【Python】動画をフレームごとの画像にして出力するスクリプトを作った話
Code 動画を画像として切り出すツールをPythonで作りました。OpenCVを利用しています。動画として視聴する必要がないコンテンツはこのツールで画像にしてしまいましょう!
3
【Python】cronを生成するモジュールを作った
Code Pythonでcron時間を生成するモジュールを作りました。タイムゾーンを引数にして生成できます。
4
【Python】シェル上で出力した文字列で濁点が分かれてしまった文字(結合文字)を濁音に直すスクリプト
Code シェル上でファイル名などを出力した際に、バがバになってしまう場合があります。それをいちいち手作業で直すのがしんどいので、直してくれるスクリプトを作りました。テストコードもあります。
5
【Python】inputを使った処理をpytestでunittestしたい(monkeypatchでmockする)
Code Pythonスクリプトをpytestする時に、input()のようなビルトイン関数が入っている時にmockする方法を紹介します。monkeypatchを使用します。
ランダム記事 ランダム