在python中为不规则图像添加边框

2024-06-26 01:41:40 发布

您现在位置:Python中文网/ 问答频道 /正文

我想添加一个边界到一个不规则的三维图像,这是一个二进制数字数组存储。我想也许可以将图像的体素左/右、前/后、上/下移动,然后组合这6个图像并减去原始图像;使用以下代码:

#make copy of the image shifted one voxel to the left
image_border = np.zeros((img_dim[0], img_dim[1], img_dim[2]))    
for x in xvoxels:
    x_slice_original = image[x, :, :]
    x_slice_new = np.zeros((img_dim[1], img_dim[2]))
    for y in yvoxels:
        for z in zvoxels:
            if x_slice_original[y, z] == 1:
                x_slice_new[(y-1), z] = 1
            else:
                x_slice_new[(y-1), z] = 0
    image_border[x, :, :] = x_slice_new

有人想知道有没有更有效的解决方案?在

编辑: 该图像为91*109*91体素的MRI图像。xvoxels和zvoxels是列表0:90,yvoxels是列表0:108


Tags: thein图像imageimgnewfornp
2条回答

这里有一个使用scipy.ndimage.binary_dilation的非常简单的方法,它本质上是您想要的操作的库版本。剩下要做的就是把原始体素清空。正如你所看到的,整件事在一条线上很舒服。在

import numpy as np
from scipy import ndimage

# create mock data
i,j,k = np.ogrid[:10,:10,:10]
ball = ((i-5)**2+(j-5)**2+(k-5)**2 < 16).view(np.int8)

# create border
shell = (ndimage.binary_dilation(ball) & ~ball).view(np.int8)

# that's all folks, show one section of original and border
print(ball[5])
# [[0 0 0 0 0 0 0 0 0 0]
#  [0 0 0 0 0 0 0 0 0 0]
#  [0 0 0 1 1 1 1 1 0 0]
#  [0 0 1 1 1 1 1 1 1 0]
#  [0 0 1 1 1 1 1 1 1 0]
#  [0 0 1 1 1 1 1 1 1 0]
#  [0 0 1 1 1 1 1 1 1 0]
#  [0 0 1 1 1 1 1 1 1 0]
#  [0 0 0 1 1 1 1 1 0 0]
#  [0 0 0 0 0 0 0 0 0 0]]
print(shell[5])
# [[0 0 0 0 0 0 0 0 0 0]
#  [0 0 0 1 1 1 1 1 0 0]
#  [0 0 1 0 0 0 0 0 1 0]
#  [0 1 0 0 0 0 0 0 0 1]
#  [0 1 0 0 0 0 0 0 0 1]
#  [0 1 0 0 0 0 0 0 0 1]
#  [0 1 0 0 0 0 0 0 0 1]
#  [0 1 0 0 0 0 0 0 0 1]
#  [0 0 1 0 0 0 0 0 1 0]
#  [0 0 0 1 1 1 1 1 0 0]]

你要做的是一个叫做“扩张”的过程。对于二值图像,其思想是循环遍历图像中的所有像素。如果像素为'True',则使其周围的指定像素集也为'True'(由'kernel'或'structure'定义)。例如

0,0,0,0,0
0,0,0,0,0
0,0,1,1,0
0,0,0,0,0
0,0,0,0,0

有核的

^{pr2}$
  1. 当达到(2,2)时,它变为:

    0,0,0,0,0
    0,0,1,0,0
    0,1,1,1,0
    0,0,1,0,0
    0,0,0,0,0
    
  2. 当达到(2,3)时,它变为:

    0,0,0,0,0
    0,0,1,1,0
    0,1,1,1,1
    0,0,1,1,0
    0,0,0,0,0
    

您可以重复此操作,或者使用其他内核。例如:

import scipy.ndimage
import numpy as np
import matplotlib.pyplot as plt

im = np.zeros((90,90),dtype='bool')
im[30:61,30:61] = True

fig = plt.figure(figsize=(18,6))
fig.set_tight_layout(True)

fig.add_subplot(1,3,1)
plt.imshow(im,interpolation='nearest')

fig.add_subplot(1,3,2)
plt.imshow(scipy.ndimage.binary_dilation(im,iterations=4),interpolation='nearest')

fig.add_subplot(1,3,3)
plt.imshow(scipy.ndimage.binary_dilation(im,iterations=4,structure=np.ones((3,3))),interpolation='nearest')

plt.show()

结果是:

enter image description here

Of course getting the 'outer' boundary is just the difference of the dilated image and the original image.

相关问题 更多 >