如何筛选图像矩阵中指定RGB值以外的像素并保留三维格式?
问题:提取非指定RGB值的像素并保留三维数组格式
我希望从图像中提取与指定RGB值不相等的像素,并且保留RGB三维数组格式,而非一维向量。使用了以下代码:
import cv2 import numpy as np image = cv2.imread('image.jpg') sought = [36,255,12] result = image[image!=sought] import sys np.set_printoptions(threshold=sys.maxsize) print(result)
得到的输出是一维向量:
[20 103 75 21 98 70 16 100 72 18 101 73 19 97 69 15 95 66 15 95 67 13 101 73 19 104 77 21 96 69 13 94 65 8 99 69 14 98 68 13 94 63 10 88 66 24 92 69 24 92 67 23 93 67 ... 99 69 14 96 66 11 91 67 25 88 65 20 92 68 14 96 69 18 96 70 16 91 64 13 95 67 13 92 64 10 90 63]
但我期望得到的是如下的三维RGB数组格式:
[[[R,G,B], [R,G,B], [R,G,B], [R,G,B]], ...... [[[R,G,B], [R,G,B], [R,G,B], [R,G,B]]]
请问哪里操作出错了?
问题原因与解决方法
错误原因
你当前代码中,image != sought是对图像的每个通道元素单独比较,得到一个与原图像同形状(H×W×3)的布尔数组。用这个布尔数组索引原图像时,numpy会将所有为True的元素扁平化提取,最终输出一维数组,这不符合你的需求。
要提取完整的RGB像素(而非单个通道值),需要先判断整个像素的三个通道是否都不等于目标值,再进行索引。
修正代码
import cv2 import numpy as np import sys image = cv2.imread('image.jpg') sought = np.array([36, 255, 12]) # 转为numpy数组,方便逐像素完整比较 # 创建掩码:判断每个像素的三个通道是否全等于目标值,取反得到需要保留的像素位置 mask = ~np.all(image == sought, axis=2) # 提取符合条件的像素,转为三维数组格式(每个元素是[R,G,B]子数组) result = image[mask].reshape(-1, 1, 3) np.set_printoptions(threshold=sys.maxsize) print(result)
代码解释
np.all(image == sought, axis=2):沿着通道维度(axis=2)判断每个像素的三个通道值是否都与目标相等,得到一个H×W的布尔数组,True表示该像素是目标值。~mask:对掩码取反,得到所有需要保留的非目标像素位置。image[mask].reshape(-1, 1, 3):提取符合条件的像素后,将形状从(N, 3)转为(N, 1, 3),得到标准的三维RGB数组格式,每个子数组对应一个[R,G,B]像素。
如果不需要额外的中间维度,直接使用result = image[mask]得到的(N, 3)数组,打印时也会显示为每行三个值的结构,同样接近你的需求。
内容的提问来源于stack exchange,提问作者korte alma
相关产品推荐
相关产品推荐

