Усредняющий фильтр при обработке изображений - PullRequest
0 голосов
/ 23 октября 2019

Мне нужна программа, которая размывает изображение, используя усредняющий фильтр. Он также должен работать с разными размерами: 3x3, 5x5 и т. Д.

Вот что у меня есть:

import cv2
import numpy as np
from matplotlib import pyplot as plt

image = cv2.imread('tranquility.jpg')

#blur = cv2.blur(image,(3,3))
width = image.shape[1]
height = image.shape[0]
result = np.zeros((image.shape[0], image.shape[1]), dtype='uint8')


def meanFilter():
    for row in range(height):
        for col in range(width):
            currentElement = 0;
            left = 0;
            right = 0;
            top = 0;
            bottom = 0;
            topLeft = 0;
            topRight = 0;
            bottomLeft = 0;
            bottomRight = 0;
            counter = 1
            currentElement = image[row][col]

            if not col - 1 < 0:
                left = image[row][col - 1]
                counter += 1
            if not col + 1 > width - 1:
                right = image[row][col + 1]
                counter += 1
            if not row - 1 < 0:
                top = image[row - 1][col]
                counter += 1
            if not row + 1 > height - 1:
                bottom = image[row + 1][col]
                counter += 1

            if not row - 1 < 0 and not col - 1 < 0:
                topLeft = image[row - 1][col - 1]
                counter += 1
            if not row - 1 < 0 and not col + 1 > width - 1:
                topRight = image[row - 1][col + 1]
                counter += 1
            if not row + 1 > height - 1 and not col - 1 < 0:
                bottomLeft = image[row + 1][col - 1]
                counter += 1
            if not row + 1 > height - 1 and not col + 1 > width - 1:
                bottomRight = image[row + 1][col + 1]
                counter += 1

            total = int(currentElement) + int(left) + int(right) + int(top) + int(bottom) + int(topLeft) + int(
                topRight) + int(bottomLeft) + int(bottomRight)
            avg = total / counter
            result[row][col] = avg


plt.subplot(121),plt.imshow(image),plt.title('Original')
plt.xticks([]), plt.yticks([])
plt.subplot(122),plt.imshow(result),plt.title('Blurred')
plt.xticks([]), plt.yticks([])
plt.show()

Вывод выглядит так:

image

По какой-то причине исходное изображение синего цвета, однако оно должно иметь нормальный цвет кожи. Кроме того, размытая версия имеет простой фиолетовый цвет. Как я могу изменить код, чтобы он размывал мое изображение нормально.

Дополнительная информация:

  1. Я имел в виду эту тему: Усредняющий фильтр с использованием python ;
  2. Используя усредняющий код фильтра здесь,на самом деле изображение размыто, но по какой-то причине оно синее. OpenCV

Обновление: Исходное изображение

1 Ответ

2 голосов
/ 24 октября 2019

Исходное изображение выглядит голубоватым, поскольку cv2.imread возвращает изображение с 3 каналами в следующем порядке: синий, зеленый и красный. plt.imshow работает с изображениями RGB, поэтому вам необходимо преобразовать исходные данные:

bgr_image = cv2.imread(your_image_filename)
rgb_image = cv2.cvtColor(bgr_image, cv2.COLOR_BGR2RGB)
plt.imshow(rgb_image)

Как заявлено Романом, вам лучше использовать библиотеку, а не кодировать фильтр. В вашем конкретном случае cv2.blur делает именно то, что вы ищете:

# 3x3 mask
blurred_image3 = cv2.blur(bgr_image, (3, 3))
cv2.imwrite('blurred_image3.png', blurred_image3)

# 5x5 mask
blurred_image5 = cv2.blur(bgr_image, (5, 5))
cv2.imwrite('blurred_image5.png', blurred_image5)

Результирующее изображение для маски 3x3:

blurred image, mask 3x3

Результирующее изображение для маски 5x5:

blurred image, mask 5x5

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...