5
3

Delete article

Deleted articles cannot be recovered.

Draft of this article would be also deleted.

Are you sure you want to delete this article?

More than 5 years have passed since last update.

二値化画像のノイズ除去と背景透過

Last updated at Posted at 2019-11-18

はじめに

前に、Pythonによる二値化画像処理の基本という記事を書いた。この記事の発展となる。

実行処理について

今回は記事の名前にもある通り、
・ノイズの除去
・背景透過
それに、
・反転画像処理
も実行

ソースコード


import cv2
import numpy as np

# 画像の読み込み
img = cv2.imread('sample2-1.png')

# グレースケール変換
gray = cv2.cvtColor(img, cv2.COLOR_RGB2GRAY)

# 閾値の設定
threshold_value = 110

# 配列の作成(output用)
threshold_img = gray.copy()

# 実装(numpy)
threshold_img[gray < threshold_value] = 0
threshold_img[gray >= threshold_value] = 255

# Output:sample2-2
cv2.imwrite(f'C:\\Users\\[username]\\python\\project1\\sample2-2.png',threshold_img)

# グレースケール変換された画像の読み込み
img = cv2.imread("sample2-2.png")
# ノイズ除去処理
ksize=3
# 中央値フィルタ
img_mask = cv2.medianBlur(img,ksize)
# 白黒反転画像
img2 = cv2.bitwise_not(img_mask)

# output:sample2-3,2-4
cv2.imwrite("C:\\Users\\[username]\\python\\project1\\sample2-3.png",img_mask)
cv2.imwrite("C:\\Users\\[username]\\python\\project1\\sample2-4.png",img2)

# 背景透過

from PIL import Image

# 画像の読み込み
org = Image.open( 'sample2-3.png' )

# サイズが同じ画像作成
trans = Image.new('RGBA', org.size, (0, 0, 0, 0))

# 縦横のサイズ
width = org.size[0]
height = org.size[1]
# for文で処理
for x in range(width):
    for y in range(height):
        pixel = org.getpixel( (x, y) )
        
        # 白色処理なし
        if pixel[0] == 255 and pixel[1] == 255 and pixel[2] == 255:
            continue
        
        # 白色以外の書き込み
        trans.putpixel( (x, y), pixel )
        
# output:sample2-5
trans.save('sample2-5.png')

内容説明

import文からoutput:sample2-2まで

これは、上記にも記載した、Pythonによる二値化画像処理の基本のコードのほぼそのままである。
画像上、閾値のみ変更。

ノイズ除去

# ノイズ除去
ksize=3
# 中央値フィルタ
img_mask = cv2.medianBlur(img,ksize)

この部分では、画像処理をする近傍の大きさ等を設定する場所である。

白黒反転処理

# 白黒反転画像
img2 = cv2.bitwise_not(img_mask)

opencvに反転処理が組み込まれており、この文のみで反転処理が可能。ちなみに今回では。白黒でしているが、本来はカラー画像でも実行可能である。

透過画像作成

# 画像の読み込み
org = Image.open( 'sample2-3.png' )

# サイズが同じ画像作成
trans = Image.new('RGBA', org.size, (0, 0, 0, 0))

# 縦横のサイズ
width = org.size[0]
height = org.size[1]
# for文で処理
for x in range(width):
    for y in range(height):
        pixel = org.getpixel( (x, y) )
        
        # 白色処理なし
        if pixel[0] == 255 and pixel[1] == 255 and pixel[2] == 255:
            continue
        
        # 白色以外の書き込み
        trans.putpixel( (x, y), pixel )

上記の#の通りの処理であるので、説明は省略する。

これらの結果sample2-1~2-5までをのせる。

元の画像(sample2-1.png)

sample2-1.png
この画像は、画像処理でよくつかわれるので見覚えのある人も多いと思う。レナと呼ばれる女性のヌード画像の一部である。
[レナについての説明 from Wikipedia](https://ja.wikipedia.org/wiki/%E3%83%AC%E3%83%8A_(%E7%94%BB%E5%83%8F%E3%83%87%E3%83%BC%E3%82%BF)

二値化画像処理(sample2-2.png)

sample2-2.png

ノイズ除去処理(sample2-3.png)

sample2-3.png

白黒反転処理(sample2-4.png)

sample2-4.png

白色以外透過処理(sample2-5.png)

sample2-5.png
この記事上ではわかりにくいので、コードのコピーなどで自分でやってみるとよい。

ソースコードの簡易化

先ほどのコードは一つ一つの処理を見やすくしていた。しかし、順番を変えることで、手順を減らすことができる。


import cv2
import numpy as np
from PIL import Image

# 画像の読み込み
img = cv2.imread('sample2-1.png')
# グレースケール変換
gray = cv2.cvtColor(img, cv2.COLOR_RGB2GRAY)
# 閾値の設定
threshold_value = 110
# 配列の作成(output用)
threshold_img = gray.copy()
# 実装(numpy)
threshold_img[gray < threshold_value] = 0
threshold_img[gray >= threshold_value] = 255

# ノイズ除去処理
ksize=3
# 中央値フィルタ
img_mask = cv2.medianBlur(img,ksize)

# 白黒反転画像
img2 = cv2.bitwise_not(img_mask)

# 背景透過
# 画像の読み込み
org = Image.open('sample2-3.png')

# サイズが同じ画像作成
trans = Image.new('RGBA', org.size, (0, 0, 0, 0))

# 縦横のサイズ
width = org.size[0]
height = org.size[1]
# for文で処理
for x in range(width):
    for y in range(height):
        pixel = org.getpixel( (x, y) )
        
        # 白色処理なし
        if pixel[0] == 255 and pixel[1] == 255 and pixel[2] == 255:
            continue
        
        # 白色以外の書き込み
        trans.putpixel( (x, y), pixel )
        
# Output:sample2-2~2-5
cv2.imwrite(f'C:\\Users\\[username]\\python\\project1\\sample2-2.png',threshold_img)
cv2.imwrite("C:\\Users\\[username]\\python\\project1\\sample2-3.png",img_mask)
cv2.imwrite("C:\\Users\\[username]\\python\\project1\\sample2-4.png",img2)
trans.save('sample2-5.png')

一括処理であるときには、Errorが起きる可能性があるが、jupyter notebookでは実行可能であった。読み込みをせずに処理内での画像を直接読み込めるので、これくらいであれば誤差に近いが早くなるだろう。

5
3
0

Register as a new user and use Qiita more conveniently

  1. You get articles that match your needs
  2. You can efficiently read back useful information
  3. You can use dark theme
What you can do with signing up
5
3

Delete article

Deleted articles cannot be recovered.

Draft of this article would be also deleted.

Are you sure you want to delete this article?