模糊处理在边沿检测和去噪声方面有较为广泛的应用。OpenCV中提供了4种模糊算法,列举如下:
- average
- median
- gaussian
- bilateral
而scipy中同样有几种方式,其本质上是没区别的。
我们先来看模糊算法的实现:
1.average
import numpy
import argparse
import cv2
image = cv2.imread('1.jpg')
cv2.imshow("Original", image)
gray = cv2.cvtColor(image, cv2.COLOR_BGR2GRAY)
cv2.imshow("Gray", gray)
#[x,y] is the kernel for bluring
#the large kernel becomes, the more blurred imag will appear
#hstack is able to stack multiple images together
#using simple mean to average
blurred = numpy.hstack([
cv2.blur(gray, (3,3)),
cv2.blur(gray, (5,5)),
cv2.blur(gray, (7,7))])
#display two images in a figure
cv2.imshow("Blurring by average", blurred)
cv2.imwrite("1_blur_by_average.jpg", blurred)
if(cv2.waitKey(0)==27):
cv2.destroyAllWindows()
2.
Gaussian
import numpy
import argparse
import cv2
image = cv2.imread('1.jpg')
cv2.imshow("Original", image)
gray = cv2.cvtColor(image, cv2.COLOR_BGR2GRAY)
cv2.imshow("Gray", gray)
#[x,y] is the kernel for bluring
#the large kernel becomes, the more blurred imag will appear
#hstack is able to stack multiple images together
#using weighted mean
#where neighborhood pixels that are closer to the central pixel contribute more "weight" to the average
blurred = numpy.hstack([
cv2.GaussianBlur(gray, (3,3), 0),
cv2.GaussianBlur(gray, (5,5), 0),
cv2.GaussianBlur(gray, (7,7), 0)])
#display two images in a figure
cv2.imshow("Blurring by Gaussian", blurred)
cv2.imwrite("1_blur_by_Gaussian.jpg", blurred)
if(cv2.waitKey(0)==27):
cv2.destroyAllWindows()
3.
median
import numpy
import argparse
import cv2
image = cv2.imread('1.jpg')
cv2.imshow("Original", image)
gray = cv2.cvtColor(image, cv2.COLOR_BGR2GRAY)
cv2.imshow("Gray", gray)
#[x,y] is the kernel for bluring
#the large kernel becomes, the more blurred imag will appear
#hstack is able to stack multiple images together
#the central pixel is replaced with the median of the neighborhood
#it is the most effective when removing salt-and-pepper noise
blurred = numpy.hstack([
cv2.medianBlur(gray, 3),
cv2.medianBlur(gray, 5),
cv2.medianBlur(gray, 7)])
#display two images in a figure
cv2.imshow("Blurring by Median", blurred)
cv2.imwrite("1_blur_by_Median.jpg", blurred)
if(cv2.waitKey(0)==27):
cv2.destroyAllWindows()
4.
bilateral
import numpy
import argparse
import cv2
image = cv2.imread('1.jpg')
cv2.imshow("Original", image)
gray = cv2.cvtColor(image, cv2.COLOR_BGR2GRAY)
cv2.imshow("Gray", gray)
#[x,y] is the kernel for bluring
#the large kernel becomes, the more blurred imag will appear
#hstack is able to stack multiple images together
#in order to reduce noise while maintaining edges
blurred = numpy.hstack([
cv2.bilateralFilter(gray, 5,21,21),
cv2.bilateralFilter(gray, 7,31,31),
cv2.bilateralFilter(gray, 9,41,41)])
#display two images in a figure
cv2.imshow("Blurring by Bilateral", blurred)
cv2.imwrite("1_blur_by_Bilateral.jpg", blurred)
if(cv2.waitKey(0)==27):
cv2.destroyAllWindows()
图像下采样,基于模糊算法再进行一定的缩放即可,这里贴下我在实验过程中用到的方法供大家参考:
为了获取不同的采样数据,我直接写成批处理,代码如下:
from PIL import Image
import os,sys
from multiprocessing import Pool
import scipy.misc as misc
import shutil
import random
import numpy as np
import cv2 as cv
# 指定输入和输出路径
input_dir = '../data/Mosaic_HR/'
output_dir = '../data/Mosaic_LR_NEW/'
scale = 4. # 4. 放大倍数
if not os.path.exists(output_dir):
os.mkdir(output_dir) # os.makedirs
image_list = os.listdir(input_dir)
image_list = [os.path.join(input_dir, _) for _ in image_list]
# 采样函数定义
def downscale(name):
print(name)
with Image.open(name) as im:
w, h = im.size
w_new = int(w / scale)
h_new = int(h / scale)
im_new = im.resize((w_new, h_new), Image.ANTIALIAS)
save_name = os.path.join(output_dir, name.split('/')[-1])
im_new.save(save_name)
def resize(image, newsize):
#methods = ['nearest','lanczos','bilinear','bicubic','cubic']
methods = ['bicubic','lanczos','bilinear','bicubic','cubic']
scale = [4, 3, 2, 1.5, 0.75, 0.5, 0.25]
#0.309090465205
value = random.random()
if (len(image.shape) == 3):
w, h, d = image.shape
else:
w, h = image.shape
s = int(value*1000) % 7
if s == 0:
image = image + np.random.random_sample(image.shape)*(int(value*100) % 50)
elif s == 1:
image = cv.blur(image, (5, 5))
elif s == 2:
image = cv.GaussianBlur(image, (5, 5), 1)
elif s == 3:
image = cv.medianBlur(image, 5)
elif s == 4:
cv.bilateralFilter(image, 9, 75, 75)
image = misc.imresize(image, newsize, methods[int(value*10)%5])
for i in range(int(value*100) % 5):
image = misc.imresize(image, (int(newsize[0]*scale[int(value*(10 ** (1+i)))%7]), int(newsize[1]*scale[int(value*(10**(1+i)))%7])), methods[int(value*(10 ** (4+i)) % 5)])
image = misc.imresize(image, newsize, methods[int(value*(10 ** (4+i)) % 10 - 5)])
return image
index = 0
def newDownscale(name):
global index
index += 1
try:
sys.stdout.write('\r>>Converting image %d/100000 ' % (index))
sys.stdout.flush()
image = misc.imread(name)
w, h, d = image.shape
w_new = int(w / scale)
h_new = int(h / scale)
image = resize(image, (w_new, h_new))
save_name = os.path.join(output_dir, name.split('/')[-1])
misc.imsave(save_name, image)
except IOError as e:
print('could not read:',name)
print('error:',e)
shutil.move(name,'/home/gavin/Desktop/face_test')
print('skip it\n')
except ValueError as err:
print('valuer Error: %s' % name )
print('error:', err)
shutil.move(name, "/home/gavin/Desktop/valueErr")
else:
shutil.move(name, '/home/gavin/Desktop/Mosaic_HR_NEW')
p = Pool(5)
p.map(newDownscale, image_list)
sys.stdout.write('Convert Over!\n')
sys.stdout.flush()
utils.py数据增强
# -*- coding: utf-8 -*-
import numpy as np
import matplotlib.pyplot as plt
import os
import random
from PIL import Image
from PIL import ImageFilter
class DataLoader(object):
def __init__(self, scale=4, crop_size=96, name=None):
self.__scale = 4
self.__crop_size = 96
self.scale = scale
self.crop_size = crop_size
self.name = name
pass
@property
def scale(self):
return self.__scale
@scale.setter
def scale(self, value):
if not isinstance(value, int):
raise ValueError("scale must be int")
elif value <= 0:
raise ValueError("scale must > 0")
else:
self.__scale = value
pass
pass
@property
def crop_size(self):
return self.__crop_size
@crop_size.setter
def crop_size(self, value):
if not isinstance(value, int):
raise ValueError("crop size must be int")
elif value <= 0:
raise ValueError("crop size must > 0")
else:
self.__crop_size = value
pass
pass
def imread(self, path):
return Image.open(path)
def resize(self, image, size):
resamples = [Image.NEAREST, Image.BILINEAR, Image.HAMMING, \
Image.BICUBIC, Image.LANCZOS]
resample = random.choice(resamples)
return image.resize(size, resample=resample)
def gaussianblur(self, image, radius=2):
return image.filter(ImageFilter.GaussianBlur(radius=radius))
def medianfilter(self, image, size=3):
return image.filter(ImageFilter.MedianFilter(size=size))
def downsampling(self, image):
resize = (image.size[0]//self.scale, image.size[1]//self.scale)
hidden_scale = random.uniform(1, 3)
hidden_resize = (int(resize[0]/hidden_scale), int(resize[1]/hidden_scale))
radius = random.uniform(1, 3)
image = self.gaussianblur(image, radius)
image = self.resize(image, hidden_resize)
image = self.resize(image, resize)
return image
def search(self, setpath):
results = []
files = os.listdir(setpath)
for file in files:
path = os.path.join(setpath, file)
results.append(path)
pass
return results
def rotate(self, lr, hr):
angle = random.choice([0, 90, 180, 270])
lr = lr.rotate(angle, expand=True)
hr = hr.rotate(angle, expand=True)
return lr, hr
def flip(self, lr, hr):
mode = random.choice([0, 1, 2, 3])
if mode == 0:
pass
elif mode == 1:
lr = lr.transpose(Image.FLIP_LEFT_RIGHT)
hr = hr.transpose(Image.FLIP_LEFT_RIGHT)
pass
elif mode == 2:
lr = lr.transpose(Image.FLIP_TOP_BOTTOM)
hr = hr.transpose(Image.FLIP_TOP_BOTTOM)
pass
elif mode == 3:
lr = lr.transpose(Image.FLIP_LEFT_RIGHT)
hr = hr.transpose(Image.FLIP_LEFT_RIGHT)
lr = lr.transpose(Image.FLIP_TOP_BOTTOM)
hr = hr.transpose(Image.FLIP_TOP_BOTTOM)
pass
return lr, hr
def crop(self, lr, hr):
hr_crop_size = self.crop_size
lr_crop_size = hr_crop_size//self.scale
lr_w = np.random.randint(lr.size[0] - lr_crop_size + 1)
lr_h = np.random.randint(lr.size[1] - lr_crop_size + 1)
hr_w = lr_w * self.scale
hr_h = lr_h * self.scale
lr = lr.crop([lr_w, lr_h, lr_w+lr_crop_size, lr_h+lr_crop_size])
hr = hr.crop([hr_w, hr_h, hr_w+hr_crop_size, hr_h+hr_crop_size])
return lr, hr
def pair(self, fp):
hr = self.imread(fp)
lr = self.downsampling(hr)
lr, hr = self.rotate(lr, hr)
lr, hr = self.flip(lr, hr)
lr, hr = self.crop(lr, hr)
lr = np.asarray(lr)
hr = np.asarray(hr)
return lr, hr
def batches(self, setpath="datasets/train", batch_size=16, complete_batch_only=False):
images = self.search(setpath)
sizes = []
for image in images:
array = plt.imread(image)
sizes.append(array.shape[0])
sizes.append(array.shape[1])
pass
crop_size_max = min(sizes)
crop_size = min(crop_size_max, self.crop_size)
if self.crop_size != crop_size:
self.crop_size = crop_size
print("Info: crop size adjusted to " + str(self.crop_size) + ".")
pass
np.random.shuffle(images)
n_complete_batches = int(len(images)/batch_size)
self.n_batches = int(len(images) / batch_size)
have_res_batch = (len(images)/batch_size) > n_complete_batches
if have_res_batch and complete_batch_only==False:
self.n_batches += 1
pass
for i in range(n_complete_batches):
batch = images[i*batch_size:(i+1)*batch_size]
lrs, hrs = [], []
for image in batch:
lr, hr = self.pair(image)
lrs.append(lr)
hrs.append(hr)
pass
lrs = np.array(lrs)
hrs = np.array(hrs)
yield lrs, hrs
if self.n_batches > n_complete_batches:
batch = images[n_complete_batches*batch_size:]
lrs, hrs = [], []
for image in batch:
lr, hr = self.pair(image)
lrs.append(lr)
hrs.append(hr)
pass
lrs = np.array(lrs)
hrs = np.array(hrs)
yield lrs, hrs
pass
pass
参考文献:
1.https://blog.youkuaiyun.com/chevroletss/article/details/49785435

本文介绍了OpenCV库中用于图像模糊处理的四种算法:平均模糊、高斯模糊、中值模糊和双边模糊,并提及scipy库中的类似方法。模糊处理常用于边沿检测和去噪声。文章提供了一段实验过程中的批处理代码示例,以实现不同采样数据的获取。
2万+

被折叠的 条评论
为什么被折叠?



