我的图像中有一堆坏点。在python中,我有一个将保存最终图像的numpy数组,还有另一个具有相同形状的boolean numpy数组,用于指示需要填充哪些像素。
我想通过取周围8个像素的平均值来填充坏点,但前提是它们实际上只有数据。例如,如果我有这个(N表示那里没有数据,?是要填充的像素):
1 2 N
N ? 2
N N 5
我会填写吗?与(1 + 2 + 2 + 5)/ 4。
现在,我使用for循环执行此操作,如下所示。 outFrame保留最终图像,而填充的是布尔数组,指示已填充了哪些像素:
# Loop through each pixel in the image
for row in range(height):
for col in range(width):
# Check to see if the pixel needs to be filled in
if not populated[row,col]:
# Check for boundary conditions
xmin = max(0,col-1)
xmax = min(width-1,col+1)
ymin = max(0,row-1)
ymax = min(height-1,row+1)
# Find the 8 surrounding values
vals = outFrame[ymin:ymax+1,xmin:xmax+1]
mask = populated[ymin:ymax+1,xmin:xmax+1]
# Find the average of only the populated pixels
if vals[mask].size != 0:
outFrame[row,col] = np.mean(vals[mask])
显然,python循环很慢,但我无法弄清任何numpy索引魔术来实现此行为。有没有办法在python中快速完成此功能?
编辑:我尝试使用opencv修复函数,如下所示:
mask = (1*~populated).astype(np.uint8)
outFrame = cv2.inpaint(outFrame,mask,3,cv2.INPAINT_NS) # This is very slow
但是,这比我的原始方法慢10倍(我的方法花费了大约3-6秒,而修复方法花费了60秒)。我的死像素非常多,我认为这是使用此方法的速度很慢的原因
编辑:这是一个示例图像。
原始图片:https://imgur.com/a/ax3nOAK
插值后:https://imgur.com/a/2apOe7p
最佳答案
很难为您提供帮助,因为您没有提供包含所有import
语句的代码的“最低完整可验证示例”,并且代码没有显示如何打开图像,甚至没有表明您使用的是OpenCV还是PIL或skimage。另外,您没有为第二个文件提供所有需要绘画的点的遮罩,也不知道您实际要实现的目标,因此,目前,我只是在尝试提供一种看起来像样的方法。对我来说,它得到的结果与您显示的结果相似。
无论如何,这是一种使用形态学的方法,在我的Mac上需要100微秒的时间-可能与您正在使用的任何方法都不一样;-)
#!/usr/bin/env python3
import cv2
import numpy as np
# Load image and make into Numpy array
im = cv2.imread('holey.png')
# Use morphology to find maximum pixel in each 3x3 square
kernel = cv2.getStructuringElement(cv2.MORPH_RECT, (3,3))
morph = cv2.morphologyEx(im, cv2.MORPH_DILATE, kernel)
# Save result
cv2.imwrite('result.png', morph)
关于python - 快速的numpy索引用于图像插值,我们在Stack Overflow上找到一个类似的问题:https://stackoverflow.com/questions/59994635/