用python实现对图像的卷积(滤波)
之前在看卷积神经网络,很好奇卷积到底是什么,最后看到了这篇文章http://blog.csdn.net/zouxy09/article/details/49080029,讲得很清楚,这篇文章中提到了对图像的滤波处理就是对图像应用一个小小的卷积核,并给出了以下例子:

对图像的卷积,opencv已经有实现的函数filter2D,注意,卷积核需要是奇数行,奇数列,这样才能有一个中心点。opencv卷积的简单实践如下:
import matplotlib.pyplot as plt
import pylab
import cv2
import numpy as np img = plt.imread("apic.jpg") #在这里读取图片 plt.imshow(img) #显示读取的图片
pylab.show() fil = np.array([[ -1,-1, 0], #这个是设置的滤波,也就是卷积核
[ -1, 0, 1],
[ 0, 1, 1]]) res = cv2.filter2D(img,-1,fil) #使用opencv的卷积函数 plt.imshow(res) #显示卷积后的图片
plt.imsave("res.jpg",res)
pylab.show()
知道了原理以后,就想自己实现一个简单的卷积,卷积的过程如下,对于mxn的图像,用kxk的滤波依次扫描,扫描的过程就是把原图的矩阵和卷积核依次进行逐点相乘(wise-element)并求和(需要注意求和结果可能大于255或小于0),在卷积特征提取ufldl讲了卷积的具体过程。
可以发现一个规律,就是卷积后的图像的大小为(m - k + 1)x(n - k + 1),写代码的时候需要根据这个规律来确定卷积后的图像的大小。

根据原理,实现代码如下:
import matplotlib.pyplot as plt
import pylab
import numpy as np def convolve(img,fil,mode = 'same'): #分别提取三个通道 if mode == 'fill':
h = fil.shape[0] // 2
w = fil.shape[1] // 2
img = np.pad(img, ((h, h), (w, w),(0, 0)), 'constant')
conv_b = _convolve(img[:,:,0],fil) #然后去进行卷积操作
conv_g = _convolve(img[:,:,1],fil)
conv_r = _convolve(img[:,:,2],fil) dstack = np.dstack([conv_b,conv_g,conv_r]) #将卷积后的三个通道合并
return dstack #返回卷积后的结果
def _convolve(img,fil): fil_heigh = fil.shape[0] #获取卷积核(滤波)的高度
fil_width = fil.shape[1] #获取卷积核(滤波)的宽度 conv_heigh = img.shape[0] - fil.shape[0] + 1 #确定卷积结果的大小
conv_width = img.shape[1] - fil.shape[1] + 1 conv = np.zeros((conv_heigh,conv_width),dtype = 'uint8') for i in range(conv_heigh):
for j in range(conv_width): #逐点相乘并求和得到每一个点
conv[i][j] = wise_element_sum(img[i:i + fil_heigh,j:j + fil_width ],fil)
return conv def wise_element_sum(img,fil):
res = (img * fil).sum()
if(res < 0):
res = 0
elif res > 255:
res = 255
return res img = plt.imread("photo.jpg") #在这里读取图片 plt.imshow(img) #显示读取的图片
pylab.show() #卷积核应该是奇数行,奇数列的
fil = np.array([[-1,-1,-1, 0, 1],
[-1,-1, 0, 1, 1],
[-1, 0, 1, 1, 1]]) res = convolve(img,fil,'fill')
print("img shape :" + str(img.shape))
plt.imshow(res) #显示卷积后的图片
print("res shape :" + str(res.shape))
plt.imsave("res.jpg",res)
pylab.show()
使用图像水平边缘滤波和浮雕滤波的结果如下,效果和opencv结果一致:


另外这里也有关于卷积c/c++实现:http://lodev.org/cgtutor/filtering.html
用python实现对图像的卷积(滤波)的更多相关文章
- 数学之路-python计算实战(19)-机器视觉-卷积滤波
filter2D Convolves an image with the kernel. C++: void filter2D(InputArray src, OutputArray dst, int ...
- 【计算机视觉】OpenCV篇(6) - 平滑图像(卷积/滤波/模糊/降噪)
平滑滤波 平滑滤波是低频增强的空间域滤波技术.空间域滤波技术即不经由傅立叶转换,直接处理影像中的像素,它的目的有两类:一类是模糊:另一类是消除噪音.空间域的平滑滤波一般采用简单平均法进行,就是求邻近像 ...
- python Tensorflow 实现图像的卷积处理
1.convolution.py import numpy as np from sklearn.datasets import load_sample_images import tensorflo ...
- [开发技巧]·Python极简实现滑动平均滤波(基于Numpy.convolve)
[开发技巧]·Python极简实现滑动平均滤波(基于Numpy.convolve) 1.滑动平均概念 滑动平均滤波法(又称递推平均滤波法),时把连续取N个采样值看成一个队列 ,队列的长度固定为N ...
- Python图像处理丨图像腐蚀与图像膨胀
摘要:本篇文章主要讲解Python调用OpenCV实现图像腐蚀和图像膨胀的算法. 本文分享自华为云社区<[Python图像处理] 八.图像腐蚀与图像膨胀>,作者: eastmount . ...
- 跟我学Python图像处理丨图像特效处理:毛玻璃、浮雕和油漆特效
摘要:本文讲解常见的图像特效处理,从而让读者实现各种各样的图像特殊效果,并通过Python和OpenCV实现. 本文分享自华为云社区<[Python图像处理] 二十四.图像特效处理之毛玻璃.浮雕 ...
- 【python图像处理】图像的缩放、旋转与翻转
[python图像处理]图像的缩放.旋转与翻转 图像的几何变换,如缩放.旋转和翻转等,在图像处理中扮演着重要的角色,python中的Image类分别提供了这些操作的接口函数,下面进行逐一介绍. 1.图 ...
- 为什么用卷积滤波,而不是非常easy的在频率领域内进行数据的频率处理
卷积.为了更好的"动态"滤波. 问题来了.为什么用卷积滤波.而不是非常easy的在频率领域内进行数据的频率处理? 为了强调我觉得的答案,已经用blog标题给出了.卷积.为了更好的& ...
- Win8Metro(C#)数字图像处理--2.10图像中值滤波
原文:Win8Metro(C#)数字图像处理--2.10图像中值滤波 [函数名称] 图像中值滤波函数MedianFilterProcess(WriteableBitmap src) [函数代码] ...
随机推荐
- Weblogic+apache多虚拟主机
p.MsoNormal,li.MsoNormal,div.MsoNormal { margin: 0cm; margin-bottom: .0001pt; text-align: justify; f ...
- Python__slots__详解
摘要 当一个类需要创建大量实例时,可以通过__slots__声明实例所需要的属性, 例如,class Foo(object): __slots__ = ['foo'].这样做带来以下优点: 更快的属性 ...
- git常见操作和常见错误
最近写了个博客demo,在上传至github时,居然报错了,刚开始学习代码上传,免不了遇到一些问题,报错信息如下: fatal: remote origin already exists. (致命错误 ...
- JavaWeb总结(七)—JSTL标签库
一.JSTL标签库介绍 JSTL标签库的使用时为了弥补HTML标签的不足,规范自定义标签的使用而诞生的.使用JSTL标签的目的是不希望在JSP中出现Java逻辑代码. 二.JSTL标签库的分类 1.核 ...
- JS高级学习路线——面向对象进阶
构造函数进阶 使用构造函数创建对象 用于创建对象 其除了是一个函数之外,我们又称之为构造对象的函数 - 简称构造函数 function Product(name,description){ //属性 ...
- var的一些理解
var 是 variable(变量,可变物)的简写.在多种编程语言中,var 被用作定义变量的关键字,在一些操作系统中也能见到它的身影.类似object,但是效率比object高一点. var是一个局 ...
- javascript核心概念之——数组
在javascript中数组就是一个可以存放任何类型的集合.存储在数组中的值用逗号分隔 var arr = ["hello",7,null,undifined,obj,undifi ...
- 深入浅出数据结构C语言版(8)——后缀表达式、栈与四则运算计算器
在深入浅出数据结构(7)的末尾,我们提到了栈可以用于实现计算器,并且我们给出了存储表达式的数据结构(结构体及该结构体组成的数组),如下: //SIZE用于多个场合,如栈的大小.表达式数组的大小 #de ...
- JS和CSS中引号的使用
font-family属性值如果是英文可以不加引号,如果是中文按照CSS标准则应该加引号,但不加引号也没关系.比如:font-family:Arial,"宋体"," ...
- struts2 之 struts2类型转换
1. 在struts2中,相比servlet来时,获取数据时,程序员没有进行手动的类型转换,类型转换工作都有struts2来完成处理,但愿对于自定义类型数据,struts2不会帮助我们完成类型转换工作 ...