如何在python中获得高斯滤波器
声明:本页面是StackOverFlow热门问题的中英对照翻译,遵循CC BY-SA 4.0协议,如果您需要使用它,必须同样遵循CC BY-SA许可,注明原文地址和作者信息,同时你必须将它归于原作者(不是我):StackOverFlow
原文地址: http://stackoverflow.com/questions/17190649/
Warning: these are provided under cc-by-sa 4.0 license. You are free to use/share it, But you must attribute it to the original authors (not me):
StackOverFlow
How to obtain a gaussian filter in python
提问by Khushboo
I am using python to create a gaussian filter of size 5x5.
I saw this post herewhere they talk about a similar thing but I didn't find the exact way to get equivalent python code to matlab function fspecial('gaussian', f_wid, sigma)Is there any other way to do it?
I tried using the following code :
我正在使用 python 创建一个大小为 5x5 的高斯滤波器。我在这里看到了这篇文章,他们谈论了类似的事情,但我没有找到将等效的 python 代码转换为 matlab 函数的确切方法fspecial('gaussian', f_wid, sigma)还有其他方法可以做到吗?我尝试使用以下代码:
size = 2
sizey = None
size = int(size)
if not sizey:
sizey = size
else:
sizey = int(sizey)
x, y = scipy.mgrid[-size: size + 1, -sizey: sizey + 1]
g = scipy.exp(- (x ** 2/float(size) + y ** 2 / float(sizey)))
print g / np.sqrt(2 * np.pi)
The output obtained is
得到的输出是
[[ 0.00730688 0.03274718 0.05399097 0.03274718 0.00730688]
[ 0.03274718 0.14676266 0.24197072 0.14676266 0.03274718]
[ 0.05399097 0.24197072 0.39894228 0.24197072 0.05399097]
[ 0.03274718 0.14676266 0.24197072 0.14676266 0.03274718]
[ 0.00730688 0.03274718 0.05399097 0.03274718 0.00730688]]
What I want is something like this:
我想要的是这样的:
0.0029690 0.0133062 0.0219382 0.0133062 0.0029690
0.0133062 0.0596343 0.0983203 0.0596343 0.0133062
0.0219382 0.0983203 0.1621028 0.0983203 0.0219382
0.0133062 0.0596343 0.0983203 0.0596343 0.0133062
0.0029690 0.0133062 0.0219382 0.0133062 0.0029690
采纳答案by ali_m
In general terms if you really care about getting the the exact same result as MATLAB, the easiest way to achieve this is often by looking directly at the source of the MATLAB function.
一般而言,如果您真的希望获得与 MATLAB 完全相同的结果,那么实现这一目标的最简单方法通常是直接查看 MATLAB 函数的源代码。
In this case, edit fspecial:
在这种情况下,edit fspecial:
...
case 'gaussian' % Gaussian filter
siz = (p2-1)/2;
std = p3;
[x,y] = meshgrid(-siz(2):siz(2),-siz(1):siz(1));
arg = -(x.*x + y.*y)/(2*std*std);
h = exp(arg);
h(h<eps*max(h(:))) = 0;
sumh = sum(h(:));
if sumh ~= 0,
h = h/sumh;
end;
...
Pretty simple, eh? It's <10mins work to port this to Python:
很简单吧?将其移植到 Python 只需 <10 分钟:
import numpy as np
def matlab_style_gauss2D(shape=(3,3),sigma=0.5):
"""
2D gaussian mask - should give the same result as MATLAB's
fspecial('gaussian',[shape],[sigma])
"""
m,n = [(ss-1.)/2. for ss in shape]
y,x = np.ogrid[-m:m+1,-n:n+1]
h = np.exp( -(x*x + y*y) / (2.*sigma*sigma) )
h[ h < np.finfo(h.dtype).eps*h.max() ] = 0
sumh = h.sum()
if sumh != 0:
h /= sumh
return h
This gives me the same answer as fspecialto within rounding error:
这给了我与fspecial舍入误差相同的答案:
>> fspecial('gaussian',5,1)
0.002969 0.013306 0.021938 0.013306 0.002969
0.013306 0.059634 0.09832 0.059634 0.013306
0.021938 0.09832 0.1621 0.09832 0.021938
0.013306 0.059634 0.09832 0.059634 0.013306
0.002969 0.013306 0.021938 0.013306 0.002969
: matlab_style_gauss2D((5,5),1)
array([[ 0.002969, 0.013306, 0.021938, 0.013306, 0.002969],
[ 0.013306, 0.059634, 0.09832 , 0.059634, 0.013306],
[ 0.021938, 0.09832 , 0.162103, 0.09832 , 0.021938],
[ 0.013306, 0.059634, 0.09832 , 0.059634, 0.013306],
[ 0.002969, 0.013306, 0.021938, 0.013306, 0.002969]])
回答by SentinalBais
This function implements functionality similar to fspecial in matlab
该函数实现了类似于matlab中fspecial的功能
http://docs.scipy.org/doc/scipy/reference/generated/scipy.signal.get_window.htmlfrom scipy import signal
http://docs.scipy.org/doc/scipy/reference/generated/scipy.signal.get_window.html来自 scipy 导入信号
>>>signal.get_window(('gaussian',2),3)
>>>array([ 0.8824969, 1. , 0.8824969])
This function appears to generate only 1D kernels
这个函数似乎只生成一维内核
I guess you could implement code to generate a Gaussian mask yourself as well as other have pointed out.
我想你可以自己和其他人指出的那样实现代码来生成高斯掩码。
回答by sparklearner
I found similar solution for this problem:
我为这个问题找到了类似的解决方案:
def fspecial_gauss(size, sigma):
"""Function to mimic the 'fspecial' gaussian MATLAB function
"""
x, y = numpy.mgrid[-size//2 + 1:size//2 + 1, -size//2 + 1:size//2 + 1]
g = numpy.exp(-((x**2 + y**2)/(2.0*sigma**2)))
return g/g.sum()
回答by Gordon Tseng
Hi I think the problem is that for a gaussian filter the normalization factor depends on how many dimensions you used.
So the filter looks like this
What you miss is the square of the normalization factor! And need to renormalize the whole matrix because of computing accuracy!
The code is attached here:
嗨,我认为问题在于,对于高斯滤波器,归一化因子取决于您使用的维度数。所以过滤器看起来像这样
你错过的是归一化因子的平方!并且由于计算精度需要对整个矩阵进行重新归一化!代码附在这里:
def gaussian_filter(shape =(5,5), sigma=1):
x, y = [edge /2 for edge in shape]
grid = np.array([[((i**2+j**2)/(2.0*sigma**2)) for i in xrange(-x, x+1)] for j in xrange(-y, y+1)])
g_filter = np.exp(-grid)/(2*np.pi*sigma**2)
g_filter /= np.sum(g_filter)
return g_filter
print gaussian_filter()
The output without normalized to sum of 1:
未归一化为 1 之和的输出:
[[ 0.00291502 0.01306423 0.02153928 0.01306423 0.00291502]
[ 0.01306423 0.05854983 0.09653235 0.05854983 0.01306423]
[ 0.02153928 0.09653235 0.15915494 0.09653235 0.02153928]
[ 0.01306423 0.05854983 0.09653235 0.05854983 0.01306423]
[ 0.00291502 0.01306423 0.02153928 0.01306423 0.00291502]]
The output divided by np.sum(g_filter):
输出除以 np.sum(g_filter):
[[ 0.00296902 0.01330621 0.02193823 0.01330621 0.00296902]
[ 0.01330621 0.0596343 0.09832033 0.0596343 0.01330621]
[ 0.02193823 0.09832033 0.16210282 0.09832033 0.02193823]
[ 0.01330621 0.0596343 0.09832033 0.0596343 0.01330621]
[ 0.00296902 0.01330621 0.02193823 0.01330621 0.00296902]]
回答by weiyixie
here is to provide an nd-gaussian window generator:
这里是提供一个 nd-gaussian 窗口生成器:
def gen_gaussian_kernel(shape, mean, var):
coors = [range(shape[d]) for d in range(len(shape))]
k = np.zeros(shape=shape)
cartesian_product = [[]]
for coor in coors:
cartesian_product = [x + [y] for x in cartesian_product for y in coor]
for c in cartesian_product:
s = 0
for cc, m in zip(c,mean):
s += (cc - m)**2
k[tuple(c)] = np.exp(-s/(2*var))
return k
this function will give you an unnormalized gaussian windows with given shape, center, and variance. for instance: gen_gaussian_kernel(shape=(3,3,3),mean=(1,1,1),var=1.0) output->
此函数将为您提供具有给定形状、中心和方差的非标准化高斯窗口。例如: gen_gaussian_kernel(shape=(3,3,3),mean=(1,1,1),var=1.0) output->
[[[ 0.22313016 0.36787944 0.22313016]
[ 0.36787944 0.60653066 0.36787944]
[ 0.22313016 0.36787944 0.22313016]]
[[ 0.36787944 0.60653066 0.36787944]
[ 0.60653066 1. 0.60653066]
[ 0.36787944 0.60653066 0.36787944]]
[[ 0.22313016 0.36787944 0.22313016]
[ 0.36787944 0.60653066 0.36787944]
[ 0.22313016 0.36787944 0.22313016]]]
回答by Sandipan Dey
You could try this too (as product of 2 independent 1D Gaussian random variables) to obtain a 2D Gaussian Kernel:
你也可以试试这个(作为 2 个独立的一维高斯随机变量的乘积)来获得一个二维高斯核:
from numpy import pi, exp, sqrt
s, k = 1, 2 # generate a (2k+1)x(2k+1) gaussian kernel with mean=0 and sigma = s
probs = [exp(-z*z/(2*s*s))/sqrt(2*pi*s*s) for z in range(-k,k+1)]
kernel = np.outer(probs, probs)
print kernel
#[[ 0.00291502 0.00792386 0.02153928 0.00792386 0.00291502]
#[ 0.00792386 0.02153928 0.05854983 0.02153928 0.00792386]
#[ 0.02153928 0.05854983 0.15915494 0.05854983 0.02153928]
#[ 0.00792386 0.02153928 0.05854983 0.02153928 0.00792386]
#[ 0.00291502 0.00792386 0.02153928 0.00792386 0.00291502]]
import matplotlib.pylab as plt
plt.imshow(kernel)
plt.colorbar()
plt.show()
回答by SCopper
Hey, I think this might help you
嘿,我想这可能对你有帮助
import numpy as np
import cv2
def gaussian_kernel(dimension_x, dimension_y, sigma_x, sigma_y):
x = cv2.getGaussianKernel(dimension_x, sigma_x)
y = cv2.getGaussianKernel(dimension_y, sigma_y)
kernel = x.dot(y.T)
return kernel
g_kernel = gaussian_kernel(5, 5, 1, 1)
print(g_kernel)
[[0.00296902 0.01330621 0.02193823 0.01330621 0.00296902]
[0.01330621 0.0596343 0.09832033 0.0596343 0.01330621]
[0.02193823 0.09832033 0.16210282 0.09832033 0.02193823]
[0.01330621 0.0596343 0.09832033 0.0596343 0.01330621]
[0.00296902 0.01330621 0.02193823 0.01330621 0.00296902]]

