Python Numpy-如何从4个输入图像中创建新图像,选择最亮的像素(最大(R+G+B))
有以下四种图像阵列:Python Numpy-如何从4个输入图像中创建新图像,选择最亮的像素(最大(R+G+B)),python,numpy,multidimensional-array,Python,Numpy,Multidimensional Array,有以下四种图像阵列: image1 = np.array([ [ # [R G B] # | | | [1, 2, 3], [11, 22, 55], [12, 45, 56] ], [ [1, 2, 3], [56, 55, 13], [12, 45, 56] ], [ [11, 22, 55], [56, 55, 13], [12, 45, 56] ], ])
image1 = np.array([
[
# [R G B]
# | | |
[1, 2, 3], [11, 22, 55], [12, 45, 56]
],
[
[1, 2, 3], [56, 55, 13], [12, 45, 56]
],
[
[11, 22, 55], [56, 55, 13], [12, 45, 56]
],
])
image2 = np.array([
[
[91, 72, 33], [111, 222, 155], [212, 245, 156]
],
[
[100, 200, 113], [56, 255, 213], [112, 145, 156]
],
[
[113, 223, 255], [156, 55, 113], [212, 245, 156]
],
])
image3 = np.array([
[
[9, 2, 3], [111, 222, 255], [22, 25, 16]
],
[
[10, 20, 13], [156, 25, 23], [12, 45, 16]
],
[
[13, 23, 155], [56, 255, 13], [222, 235, 216]
],
])
image4 = np.array([
[
[29, 22, 23], [111, 222, 255], [223, 125, 216]
],
[
[210, 220, 13], [156, 252, 232], [122, 145, 216]
],
[
[123, 232, 155], [56, 255, 213], [222, 235, 216]
],
])
对于每一行和每一列,我想计算图像阵列的红色、绿色和蓝色通道之和的最大RGB值,并使用最大值构建一个新的图像阵列
所以在尝试了下面的代码之后,它得到了重复的索引,因为在每行和每列中,三个图像数组的最大RGB可能是重复的。但我只想得到第一个匹配索引
array = np.array([image1, image2, image3, image4])
array_sum = array.sum(axis=3)
# array_sum_max_index = array_sum.argmax(axis=0)
indices = np.where(array_sum == array_sum.max(axis=0))
print(indices)
输出
(array([1, 1, 1, 2, 2, 3, 3, 3, 3, 3, 3]), array([0, 0, 2, 0, 2, 0, 1, 1, 1, 2, 2]), array([0, 2, 0, 1, 2, 1, 0, 1, 2, 1, 2]))
在这方面也有类似的答案,但它不能解决我的问题。因此,如何在索引首次匹配时获取索引
编辑:
输入图像的实际数量超过32个。涉及numpy.choose的解决方案可能无法正常工作,因此您可以使用:
这将为您提供每个位置最亮的最高R+G+B像素:
array([[196, 588, 613],
[443, 640, 483],
[591, 524, 673]])
结果与array_sum.maxaxis=0相同。我想这就是您要寻找的:
np.choose(array_sum_max_index[...,None], tuple(array))
输出:
说明:
array_sum_max_index的形状为m,n,其中每个图像都是形状为m,n,3的数组
数组是形状为4,m,n,3的数组,tuplearray的每个元素都是形状为m,n,3的子数组
我们尝试使用np.choose,将数组\u sum\u max\u索引作为选择器数组传递,将tuplearray作为选择器将从中选择的子数组序列。但是正如您在numpy.choose的文档中所看到的,选择器数组和从中选择的子数组必须都可以一起广播。由于选择器数组数组_sum_max_index的形状为m,n,为了使其可以与形状为m,n,3的子数组一起广播,我们使用表达式数组_sum_max_index[…,None]向数组_sum_max_index追加一个额外的单位长度维度
如果我们只使用数组而不是tuplearray,这仍然有效,但是numpy.choose的文档不鼓励这样做
提出一个不使用numpy.choose的替代解决方案,因为OP已经指出在numpy.choose的情况下32个choose数组的约束是一个问题
array = np.array([image1, image2, image3, image4])
array_sum = array.sum(axis=3)
array_sum_max_index = array_sum.argmax(axis=0)
m = 3 # Number of pixel rows
n = 3 # Number of pixel columns
array[array_sum_max_index, np.arange(m)[:,None,], np.arange(n)[None,:]]
输出:
根据@fountainhead的回答,在一行中:
np.take_along_axis(array, array.sum(3).argmax(0)[None, ..., None], 0)
Out[]:
array([[[[ 91, 72, 33],
[111, 222, 255],
[212, 245, 156]],
[[210, 220, 13],
[156, 252, 232],
[122, 145, 216]],
[[113, 223, 255],
[ 56, 255, 213],
[222, 235, 216]]]])
array\u sum\u max\u index或array\u sum.maxaxis=0如何不满足您的需要?在我看来这是正确的,但也许我误解了你的目标。array_sum_max_index给出array[[1,2,1],[3,3,3],[1,3,2]]告诉您每个像素处哪个图像最亮,array_sum.maxaxis=0给出从每个位置的所有图像中获取的最亮像素。我想使用最大RGB生成一个新数组,但是,如何通过数组_sum_max_索引访问数组对我来说很难。您出于某种原因注释掉的线数组_sum_max_索引=数组_sum.argmaxaxis=0正好提供了您在问题中要求的3,3新图像数组。是的,数组_sum_max_索引是正确的答案,但我不知道如何使用它访问数组。所以我试着从哪里获取索引,返回索引。我认为真正需要的是np.choosarray\u sum\u max\u index,数组。不,不太需要。在数组_sum_max_索引返回中,每个行和列的编号表示数组的最大RGB索引。因此,我可以通过array\u sum\u max\u index return生成一个新数组,但这对我来说很难。是的,但是numpy.choose允许至少0个最多32个数组对象通过。所以x的形状。。。对于数组,x必须介于0和32之间。@luneice-是否要将32个以上的图像传递给np。选择从中进行选择?是的,当传递32个以上的图像时,它得到了ValueError:至少需要0个,最多需要32个数组对象。在这种情况下,您需要将所有这些代码包装到一个函数中,并多次调用该函数。因此,如果您有50个图像,那么对函数的第一次调用将返回一个使用前32个图像中最亮像素的新图像。对函数的下一次调用必须传递此返回图像和剩余的18个图像,才能获得使用所有50个图像中最亮像素的最终图像。@luneice-我发布了一个不使用numpy.choose的不同答案。请看一看,很好。想想这些学习的日子,我一直在寻找numpy的真实世界用例!它是为这个用例设计的,但是它可能非常笨拙,因为需要数组和索引具有相同的维数,因此[None,…,None]
array = np.array([image1, image2, image3, image4])
array_sum = array.sum(axis=3)
array_sum_max_index = array_sum.argmax(axis=0)
m = 3 # Number of pixel rows
n = 3 # Number of pixel columns
array[array_sum_max_index, np.arange(m)[:,None,], np.arange(n)[None,:]]
array([[[ 91, 72, 33],
[111, 222, 255],
[212, 245, 156]],
[[210, 220, 13],
[156, 252, 232],
[122, 145, 216]],
[[113, 223, 255],
[ 56, 255, 213],
[222, 235, 216]]])
np.take_along_axis(array, array.sum(3).argmax(0)[None, ..., None], 0)
Out[]:
array([[[[ 91, 72, 33],
[111, 222, 255],
[212, 245, 156]],
[[210, 220, 13],
[156, 252, 232],
[122, 145, 216]],
[[113, 223, 255],
[ 56, 255, 213],
[222, 235, 216]]]])