如何在 octave / matlab 的多维数组中找到所有具有相同值的单元格
How can I find all the cells that have the same values in a multi-dimensional array in octave / matlab
如何在多维数组中找到所有具有相同值的单元格?
我可以部分使用 result=A(:,:,1)==A(:,:,2) 但我不确定如何还包括 A(:,:,3)
我尝试了 result=A(:,:,1)==A(:,:,2)==A(:,:,3) 但结果全为 0什么时候应该有 1 个正确答案
这是数字 8 位于数组所有页面上的同一单元格中的位置。注意:这只是一个测试,重复的数字可以多次找到并且是不同的数字。
PS:我使用的是 octave 3.8.1,它类似于 matlab
查看下面的代码:
clear all, tic
%graphics_toolkit gnuplot %use this for now it's older but allows zoom
A(:,:,1)=[1 2 3; 4 5 6; 7 9 8]; A(:,:,2)=[9 1 7; 6 5 4; 7 2 8]; A(:,:,3)=[2 4 6; 8 9 1; 3 5 8]
[i j k]=size(A)
for ii=1:k
maxamp(ii)=max(max(A(:,:,ii)))
Ainv(:,:,ii)=abs(A(:,:,ii)-maxamp(ii));%the extra max will get the max value of all values in array
end
%result=A(:,:,1)==A(:,:,2)==A(:,:,3)
result=A(:,:,1)==A(:,:,2)
result=double(result); %turns logical index into double to do find
[row col page] = find(result) %gives me the col, row, page
这是它给我的输出:
>>>A =
ans(:,:,1) =
1 2 3
4 5 6
7 9 8
ans(:,:,2) =
9 1 7
6 5 4
7 2 8
ans(:,:,3) =
2 4 6
8 9 1
3 5 8
i = 3
j = 3
k = 3
maxamp = 9
maxamp =
9 9
maxamp =
9 9 9
result =
0 0 0
0 1 0
1 0 1
row =
3
2
3
col =
1
2
3
page =
1
1
1
你可以做到
result = A(:,:,1) == A(:,:,2) & A(:,:,1) == A(:,:,3);
使用bsxfun
(MATLAB doc, Octave doc) and check to see if broadcasting the first slice is equal across all slices with a call to all
(MATLAB doc, Octave doc):
B = bsxfun(@eq, A, A(:,:,1));
result = all(B, 3);
如果我们正在玩 code golf,一个班轮可能是:
result = all(bsxfun(@eq, A, A(:,:,1)), 3);
上述方法的美妙之处在于,您可以在三维中拥有任意数量的切片,而不仅仅是三个。
例子
%// Your data
A(:,:,1)=[1 2 3; 4 5 6; 7 9 8];
A(:,:,2)=[9 1 7; 6 5 4; 7 2 8];
A(:,:,3)=[2 4 6; 8 9 1; 3 5 8];
B = bsxfun(@eq, A, A(:,:,1));
result = all(B, 3);
... 给我们:
>> result
result =
0 0 0
0 0 0
0 0 1
以上是有道理的,因为所有切片的第三行和第三列是每个切片共享相同值(即 8)的唯一值。
这是另一种方法:沿三维计算差异并检测何时所有这些差异都为零:
result = ~any(diff(A,[],3),3);
sum
沿第三个维度的元素并将其除以维度数。如果所有维度的值都相同,我们将取回原始值。否则为不同的(例如十进制)值。然后找到A
和求和在第三个维度上相等的位置。
all( A == sum(A,3)./size(A,3),3)
ans =
0 0 0
0 0 0
0 0 1
或
你也可以
all(A==repmat(sum(A,3)./size(A,3),[1 1 size(A,3)]),3)
与 A
相比,repmat(sum(A,3)./size(A,3),[1 1 size(A,3)])
会突出显示隐式广播。
或
你完全跳过广播,只将它与 A
的第一片进行比较
A(:,:,1) == sum(A,3)./size(A,3)
说明
3
代表三维。
sum(A,3)
表示我们正在对第三个维度求和。
然后我们将该总和除以维数。
它基本上是该位置在三维空间中的平均值。
如果您将三个值相加然后除以三,那么您将得到原始值。
例如,A(3,3,:)
是 [8 8 8]
。 (8+8+8)/3 = 8
。
如果再举一个例子,即上面的值,A(2,3,:) = [6 4 1]
。
然后(6+4+1)/3=3.667
。这不等于 A(2,3,:)
.
sum(A,3)./size(A,3)
ans =
4.0000 2.3333 5.3333
6.0000 6.3333 3.6667
5.6667 5.3333 8.0000
因此,我们知道元素是不一样的
贯穿整个三维空间。这只是我使用的一个技巧
确定那个。你还必须记住
sum(A,3)./size(A,3)
本来就是一个3x3x1
矩阵
将自动扩展(即广播)到
当我们与 A
(A == sum(A,3)./size(A,3)
) 进行比较时,3x3x3
矩阵。
该比较的结果将是一个逻辑数组,其中 1
表示在整个第三维中相同的位置。
A == sum(A,3)./size(A,3)
ans =
ans(:,:,1) =
0 0 0
0 0 0
0 0 1
ans(:,:,2) =
0 0 0
1 0 0
0 0 1
ans(:,:,3) =
0 0 0
0 0 0
0 0 1
然后使用 all(....,3)
获得这些。结果是 3x3x1
矩阵,其中 1
表示值与
第三维。
all( A == sum(A,3)./size(A,3),3)
ans =
0 0 0
0 0 0
0 0 1
如何在多维数组中找到所有具有相同值的单元格?
我可以部分使用 result=A(:,:,1)==A(:,:,2) 但我不确定如何还包括 A(:,:,3) 我尝试了 result=A(:,:,1)==A(:,:,2)==A(:,:,3) 但结果全为 0什么时候应该有 1 个正确答案 这是数字 8 位于数组所有页面上的同一单元格中的位置。注意:这只是一个测试,重复的数字可以多次找到并且是不同的数字。
PS:我使用的是 octave 3.8.1,它类似于 matlab
查看下面的代码:
clear all, tic
%graphics_toolkit gnuplot %use this for now it's older but allows zoom
A(:,:,1)=[1 2 3; 4 5 6; 7 9 8]; A(:,:,2)=[9 1 7; 6 5 4; 7 2 8]; A(:,:,3)=[2 4 6; 8 9 1; 3 5 8]
[i j k]=size(A)
for ii=1:k
maxamp(ii)=max(max(A(:,:,ii)))
Ainv(:,:,ii)=abs(A(:,:,ii)-maxamp(ii));%the extra max will get the max value of all values in array
end
%result=A(:,:,1)==A(:,:,2)==A(:,:,3)
result=A(:,:,1)==A(:,:,2)
result=double(result); %turns logical index into double to do find
[row col page] = find(result) %gives me the col, row, page
这是它给我的输出:
>>>A =
ans(:,:,1) =
1 2 3
4 5 6
7 9 8
ans(:,:,2) =
9 1 7
6 5 4
7 2 8
ans(:,:,3) =
2 4 6
8 9 1
3 5 8
i = 3
j = 3
k = 3
maxamp = 9
maxamp =
9 9
maxamp =
9 9 9
result =
0 0 0
0 1 0
1 0 1
row =
3
2
3
col =
1
2
3
page =
1
1
1
你可以做到
result = A(:,:,1) == A(:,:,2) & A(:,:,1) == A(:,:,3);
使用bsxfun
(MATLAB doc, Octave doc) and check to see if broadcasting the first slice is equal across all slices with a call to all
(MATLAB doc, Octave doc):
B = bsxfun(@eq, A, A(:,:,1));
result = all(B, 3);
如果我们正在玩 code golf,一个班轮可能是:
result = all(bsxfun(@eq, A, A(:,:,1)), 3);
上述方法的美妙之处在于,您可以在三维中拥有任意数量的切片,而不仅仅是三个。
例子
%// Your data
A(:,:,1)=[1 2 3; 4 5 6; 7 9 8];
A(:,:,2)=[9 1 7; 6 5 4; 7 2 8];
A(:,:,3)=[2 4 6; 8 9 1; 3 5 8];
B = bsxfun(@eq, A, A(:,:,1));
result = all(B, 3);
... 给我们:
>> result
result =
0 0 0
0 0 0
0 0 1
以上是有道理的,因为所有切片的第三行和第三列是每个切片共享相同值(即 8)的唯一值。
这是另一种方法:沿三维计算差异并检测何时所有这些差异都为零:
result = ~any(diff(A,[],3),3);
sum
沿第三个维度的元素并将其除以维度数。如果所有维度的值都相同,我们将取回原始值。否则为不同的(例如十进制)值。然后找到A
和求和在第三个维度上相等的位置。
all( A == sum(A,3)./size(A,3),3)
ans =
0 0 0
0 0 0
0 0 1
或
你也可以
all(A==repmat(sum(A,3)./size(A,3),[1 1 size(A,3)]),3)
与 A
相比,repmat(sum(A,3)./size(A,3),[1 1 size(A,3)])
会突出显示隐式广播。
或
你完全跳过广播,只将它与 A
A(:,:,1) == sum(A,3)./size(A,3)
说明
3
代表三维。
sum(A,3)
表示我们正在对第三个维度求和。
然后我们将该总和除以维数。
它基本上是该位置在三维空间中的平均值。
如果您将三个值相加然后除以三,那么您将得到原始值。
例如,A(3,3,:)
是 [8 8 8]
。 (8+8+8)/3 = 8
。
如果再举一个例子,即上面的值,A(2,3,:) = [6 4 1]
。
然后(6+4+1)/3=3.667
。这不等于 A(2,3,:)
.
sum(A,3)./size(A,3)
ans =
4.0000 2.3333 5.3333
6.0000 6.3333 3.6667
5.6667 5.3333 8.0000
因此,我们知道元素是不一样的
贯穿整个三维空间。这只是我使用的一个技巧
确定那个。你还必须记住
sum(A,3)./size(A,3)
本来就是一个3x3x1
矩阵
将自动扩展(即广播)到
当我们与 A
(A == sum(A,3)./size(A,3)
) 进行比较时,3x3x3
矩阵。
该比较的结果将是一个逻辑数组,其中 1
表示在整个第三维中相同的位置。
A == sum(A,3)./size(A,3)
ans =
ans(:,:,1) =
0 0 0
0 0 0
0 0 1
ans(:,:,2) =
0 0 0
1 0 0
0 0 1
ans(:,:,3) =
0 0 0
0 0 0
0 0 1
然后使用 all(....,3)
获得这些。结果是 3x3x1
矩阵,其中 1
表示值与
第三维。
all( A == sum(A,3)./size(A,3),3)
ans =
0 0 0
0 0 0
0 0 1