如何有效地循环通过每个像素为节省时间与numpy?

6bc51xsx  于 2022-12-04  发布在  其他
关注(0)|答案(3)|浏览(116)

正如你所知,循环遍历每个像素并使用opencv访问它们的值需要太长的时间。作为一个初学者,我自己也在尝试学习opencv,当我尝试这种方法时,我花了大约7-10秒的时间来循环遍历图像并执行操作。
代码如下

original_image = cv2.imread(img_f)

image = np.array(original_image)
for y in range(image.shape[0]):
    for x in range(image.shape[1]):
        # remove grey background
        if 150 <= image[y, x, 0] <= 180 and \
                150 <= image[y, x, 1] <= 180 and \
                150 <= image[y, x, 2] <= 180:
            image[y, x, 0] = 0
            image[y, x, 1] = 0
            image[y, x, 2] = 0

        # remove green dashes
        if image[y, x, 0] == 0 and \
                image[y, x, 1] == 169 and \
                image[y, x, 2] == 0:
            image[y, x, 0] = 0
            image[y, x, 1] = 0
            image[y, x, 2] = 0

在上面的代码中,我只是想删除灰色和绿色像素颜色。
我发现类似的问题问here,但我不能理解如何在我的用例中使用numpy,因为我是python和numpy的初学者。
任何帮助或建议,以解决这一点将不胜感激,谢谢

nnsrf1az

nnsrf1az1#

您可以利用NumPy的矢量化操作来消除所有循环,这应该会快得多。

# Remove grey background
is_grey = ((150 <= image) & (image <= 180)).all(axis=2, keepdims=True)
image = np.where(is_grey, 0, image)

# Remove green dashes
is_green_dash = (image[..., 0] == 0) & (image[..., 1] == 169) & (image[..., 2] == 0)
is_green_dash = is_green_dash[..., np.newaxis]  # append a new dim at the end
image = np.where(is_green_dash, 0, image)

np.where的两个调用都依赖于NumPy的broadcasting

nzrxty8p

nzrxty8p2#

提高代码性能的一种方法是使用cv2.inRange()函数查找具有所需颜色的像素,然后使用cv2.bitwise_and()函数从图像中删除这些像素。这样做比逐个遍历每个像素效率更高,因为逐个遍历每个像素可能会很慢,而且计算量很大。下面是一个实现方法的示例:

import cv2
import numpy as np

# Read the image
original_image = cv2.imread('image.jpg')

# Define the colors to be removed as ranges of BGR values
grey_min = np.array([150, 150, 150], np.uint8)
grey_max = np.array([180, 180, 180], np.uint8)
green_min = np.array([0, 0, 0], np.uint8)
green_max = np.array([0, 169, 0], np.uint8)

# Use inRange() to find pixels with the desired colors
grey_mask = cv2.inRange(original_image, grey_min, grey_max)
green_mask = cv2.inRange(original_image, green_min, green_max)

# Use bitwise_and() to remove the pixels with
xsuvu9jc

xsuvu9jc3#

您可以对图像应用numpy过滤。在您的方案中,它将是:

mask_gray = (
    (150 <= image[:, :, 0]) & (image[:, :, 0] <= 180) & 
    (150 <= image[:, :, 1]) & (image[:, :, 1] <= 180) & 
    (150 <= image[:, :, 2]) & (image[:, :, 2] <= 180)
)

image[mask_gray] = 0

mask_green = (
    (image[:, :, 0] == 0) &
    (image[:, :, 1] == 169) &
    (image[:, :, 2] == 0)
)

image[mask_green] = 0

这里的mask_graymask_green是布尔掩码

相关问题