如何从此图像中提取此明显事件?

时间:2015-03-25 06:58:52

标签: python image-processing numpy statistics signal-processing

编辑:我找到了解决方案:D感谢您的帮助。

我创建了一个图像处理算法,从数据中提取该图像。它很复杂,所以我不会详细说明,但这个图像本质上是一个巨大的numpy数组(它可视化对象像素强度的角度依赖性)。

我想写一个自动确定曲线何时切换方向的程序。我有数据,我也有这个图像,但事实证明做一些有意义的事情要么很棘手。阈值处理失败,因为存在不同背景颜色的条带。由于同样的原因,Sobel算子和Hough变换也不能很好地工作。

人们很容易看到这种切换何时发生,但不容易告诉计算机。有小费吗?谢谢!

Tricky!

编辑:谢谢大家,我现在在使用结果的一般高斯和骨架化进行卷积后,将线条拟合到此图像。关于这样做的任何指示将不胜感激:)

Skeletonized!

3 个答案:

答案 0 :(得分:3)

您可以采用连续列的加权点积来获得更容易使用的一维信号。您可以使用此信号提取模式:

enter image description here

import numpy as np
A = np.loadtxt("img.txt")
N = A.shape[0]
L = np.logspace(1,2,N)
X = []
for c0,c1 in zip(A.T, A.T[1:]):
    x = c0.dot(c1*L) / (np.linalg.norm(c0)*np.linalg.norm(c1))
    X.append(x)

X = np.array(X)

import pylab as plt

plt.matshow(A,alpha=.5)
plt.plot(X*3-X.mean(),'k',lw=2)
plt.axis('tight')
plt.show()

这绝对不是这个问题的完整答案,而是一个有用的观察,对评论来说太长了。如果有更好的答案,我会删除。

答案 1 :(得分:2)

在Mark McCurry的帮助下,我取得了不错的成绩。

Original

步骤1:加载原始图像。通过从自身中减去每个垂直列的中位数来删除背景。

no_background=[]
for i in range(num_frames):
    no_background.append(orig[:,i]-np.median(orig,1))
no_background=np.array(no_background).T

Subtracted median.

步骤2:将负值更改为0。

clipped_background = no_background.clip(min=0)

Clipped negative values.

步骤3:提取1D信号。取垂直列的加权和,它将列中的最大强度与其位置相关联。

def exp_func(x):
    return np.dot(np.arange(len(x)), np.power(x, 10))/(np.sum(np.power(x, 10)))

weighted_sum = np.apply_along_axis(exp_func,0, clipped_background)

Signal

步骤4:获取1D信号的导数。

conv = np.convolve([-1.,1],weighted_sum, mode='same')
pl.plot(conv)

1D Derivative

步骤5:确定衍生物何时改变符号。

signs=np.sign(conv)
pl.plot(signs)
pl.ylim(-1.2,1.2)

Convolution

步骤6:将中值滤波器应用于上述信号。

filtered_signs=median_filter(signs, 5) #pick window size based on result. second arg and odd number.
pl.plot(filtered_signs)
pl.ylim(-1.2,1.2)

Median Filter

步骤7:找到符号切换时的索引(帧位置)。绘制结果。

def sign_switch(oneDarray):
    inds=[]
    for ind in range(len(oneDarray)-1):
        if (oneDarray[ind]<0 and oneDarray[ind+1]>0) or (oneDarray[ind]>0 and oneDarray[ind+1]<0):
            inds.append(ind)
    return np.array(inds)

switched_frames = sign_switch(filtered_signs)

Final Result

答案 2 :(得分:0)

对于探测尖端位置或转折点,您可以尝试在原始图像上使用角点检测器(而不是骨架图像)。作为角点检测器,结构张量可以适用。结构张量对于计算图像中的局部方向也很有用。