使用 numpy 确定 RGB 图像的某些部分是彩色还是灰度

Determine if certain parts of an RGB image are colored or grayscale using numpy

我正在尝试使用 python、opencv 和 numpy 库来确定 RGB 图像的某些部分是彩色的还是灰度的。更具体地说,在 RGB 图像中,我使用神经网络确定面部位置,当该图像包含打印照片时,我想知道该图像中的面部位置是灰度还是彩色。

到目前为止我尝试了什么:

            red_average = np.average(rgb_image_crop[:,:,0])
            green_average = np.average(rgb_image_crop[:,:,1])
            blue_average = np.average(rgb_image_crop[:,:,2])

            highest_distance = max(abs(red_average-green_average), abs(red_average-blue_average), abs(green_average-blue_average))
            if highest_distance> 15:
                print("this crop is colored")
            else:
                print("this crop is grayscale")

找到人脸位置后,人脸被裁剪并命名为“rgb_image_crop”。我基本上使用 numpy 拆分 R、G、B 通道并分别取平均值。我的逻辑是,与彩色图像相比,灰度图像的 R、G、B 像素值彼此接近,这种方法的性能一般。

但我想知道是否有比这更复杂的方法更有希望取得更高的成功?我查看了其他问题,但每个人都只是问确定图像文件是 B/W 还是 RGB。

总结结果后编辑: 我在计算机视觉中尝试了各种方法,然后尝试使用我创建的数据集训练 CNN 分类器。显然 CNN 网络不能学到太多颜色,但他们主要学习纹理,结果真的很令人失望。我训练了一个基于 Darknet YOLOV4 的分类器,并且用现实生活中的例子进行测试未能给出令人满意的结果。 Mark 的建议是最稳定的建议,其次是我在问题中提到的建议。我将尝试使用硬件加速来实现 Mark 的解决方案,并使其使用更少的 CPU 资源。

如何找到裁剪图像的每个像素的最大差异,然后获取它们的 STD。对于灰度图像,该值与彩色图像相比必须较小。

您可以在第 3 个维度上使用 Numpy 峰到峰 来获得每个像素位置的最小和最大 RGB 值之间的差异。然后设定阈值并计算异常值:

RGBrange = np.ptp(im, axis=2)
coloured = RGBrange > 10

您可能还会得到一些想法here