如何解决图像X轴的导数中位数
我使用不同的方法来计算导数,例如:
- 与数组[[-1,1]]进行卷积。
- 使用傅立叶定理,通过计算上述图像和阵列的DFT,将它们相乘并执行IDFT。
- 直接通过导数公式(计算傅立叶,乘以索引和常数并计算逆数)。
所有方法似乎几乎相同,但有细微差别。
最好解释一下为什么它们最终会有不同的结果。
计算完这些后,我开始研究结果以了解它,然后发现一些令我困惑的东西:
让我感到困惑的主要是,当我尝试计算该导数的中位数时,其始终为0.0。
那是为什么?
我添加了用于计算此代码的代码(至少是第一种方法),因为可能是我做错了。
from scipy.signal import convolve2d
im = sl.read_image(r'C:\Users\ahhal\Desktop\Essentials\Uni\year3\Semestera\ImageProcessing\Exercises\Ex2\external\monkey.jpg',1)
b = [[-1,1]]
print(np.median(convolve2d(im,b)))
输出:0.0
read_image
函数是我自己的,这是实现:
from imageio import imread
from skimage.color import rgb2gray
import numpy as np
def read_image(filename,representation):
"""
Receives an image file and converts it into one of two given representations.
:param filename: The file name of an image on disk (Could be grayscale or RGB).
:param representation: representation code,either 1 or 2 defining wether the output
should be a grayscale image (1) or an RGB image (2). If the input image is grayscale,we won't call it with representation = 2.
:return: An image,represented by a matrix of type (np.float64) with intensities
normalized to the range [0,1].
"""
assert representation in [1,2]
# reads the image
im = imread(filename)
if representation == 1: # If the user specified they need grayscale image,if len(im.shape) == 3: # AND the image is not grayscale yet
im = rgb2gray(im) # convert to grayscale (**Assuming its RGB and not a different format**)
im_float = im.astype(np.float64) # Convert the image type to one we can work with.
if im_float.max() > 1: # If image values are out of bound,normalize them.
im_float = im_float / 255
return im_float
修改2: 我在几个不同的图像上进行了尝试,所有图像都得到了0.0。 我在示例中使用的图像是:
解决方法
我使用不同的方法来计算导数,例如:
- 与数组[[-1,1]]进行卷积。
- 使用傅立叶定理,通过计算上述图像和阵列的DFT,将它们相乘并执行IDFT。
- 直接通过导数公式(计算傅立叶,乘以索引和常数并计算逆数)。
这些导数方法都是近似的,并且有不同的假设:
-
[[-1,1]]的卷积计算相邻元素之间的差异,
derivative ~= data[n+1] − data[n]
您可以将其解释为类似于使用线段对数据进行插值,然后采用该插值的导数:
I(x) = data[n] + (data[n+1] − data[n]) * (x − n)
因此,近似值假设基础函数是局部线性的。您可以通过泰勒展开来分析错误,以发现错误来自被忽略的高阶项。换句话说,只要函数没有强非线性项,则近似值是准确的。这是finite differences的简单情况。
-
这与1相同,除了具有不同的边界处理以处理图像边缘附近的样本卷积。默认情况下,scipy.signal.convolve2d进行零填充(尽管您可以使用
boundary
选项来选择其他方法)。但是,当通过DFT计算卷积时,隐式地边界处理是周期性的,在图像边缘处回绕。因此,由于边界处理的不同,边缘附近像素边缘的1和2的结果也不同。 -
在DFT表示下通过乘以iω来计算导数可以解释为类似于评估数据sinc interpolation的导数。 Sinc插值假定数据为band limited。误差来自超出奈奎斯特频率的光谱。特别是,如果从对象边界开始存在硬跳跃不连续性,则图像将不会受到带宽限制,并且基于DFT的导数在跳跃附近将具有相当大的误差,表现为振铃伪影。
让我感到困惑的主要是,当我尝试计算该导数的中位数时,其始终为0.0。
我不知道为什么会在这里发生,但并非总是如此。例如,如果每个图像行都是单位坡度data[n] = n
,则除[[-1,1]]的卷积在所有地方都等于1,除非取决于边界处理(可能不在边缘),所以中位数为1
Pascal already gave a wonderful explanation导数的各种近似之间的差异。因此,我将集中在“为什么总是0.0?”问题。
仅通过近似,导数的中位数为0.0。在计算时,基于有限差分近似(方法1),我得到-5.15e-5作为中位数。接近零,但不完全是零。
在图像的均匀(平坦)区域(例如散焦背景)中,导数为0。图像中的其他特征倾向于同时具有正边缘和负边缘,从而使导数图像的直方图非常对称:
这种对称性导致此类图像的中值(以及均值)接近于零。然而,这并非总是如此。例如,如果图像的左边缘比右边缘(或相反方向)亮,则图像上必须存在净梯度,从而导致均值或中位数不同于零。
版权声明:本文内容由互联网用户自发贡献,该文观点与技术仅代表作者本人。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如发现本站有涉嫌侵权/违法违规的内容, 请发送邮件至 dio@foxmail.com 举报,一经查实,本站将立刻删除。