问题
I need to effectively eliminate consecutive regions in vector "a" or better in rows/columns of matrix "A" with length of separate ones regions greater than positive integer N <= length(A):
See following example:
N = 2 % separate consecutive regions with length > 2 are zeroed
a = [0 1 1 0 0 1 1 1 0 0 1 1 1 1 0 1]
a_elim = [0 1 1 0 0 0 0 0 0 0 0 0 0 0 0 1]
or 2D case:
N = 2
A = [1 0 1 …
1 1 0 …
1 1 0 …
0 0 1 …
1 1 1]
% elimination over columns
A_elim= 0 0 1
0 1 0
0 1 0
0 0 1
1 1 1
% elimination over rows
A_elim= 1 0 1
1 1 0
1 1 0
0 0 1
0 0 0
I am looking for effective vectorized MATLAB function performing this task for size(A) ~ [100000, 1000] (over columns case).
回答1:
You can use a convolution:
For the 1D case:
N = 2 %tolerance
A = [0 1 1 0 0 1 1 1 0 0 1 1 1 1 0 1]
ind = conv(A,ones(N+1,1),'same');
%ind = 1 2 2 1 1 2 3 2 1 1 2 3 3 2 2 1
%A = 0 1 1 0 0 1 1 1 0 0 1 1 1 1 0 1
ind = conv(ind>N,ones(N+1,1),'same')>0;
%ind = 0 0 0 0 0 1 1 1 0 0 1 1 1 1 0 0
%A = 0 1 1 0 0 1 1 1 0 0 1 1 1 1 0 1
A(ind) = 0
if N is odd you need an extra step:
ind = conv(A,ones(N+1,1),'same');
ind(find(ind==N+1)+1) = N+1 %the extra step
ind = conv(ind>N,ones(N+1,1),'same')>0;
Generalization for nD dimension:
N = 3 %tolerance
A = round(rand(5,5,5));
for ii = 1:ndims(A)
conv_vec = permute(ones(N+1,1),circshift([1:ndims(A)],ii-1,2))
ind = convn(A,conv_vec,'same')
if mod(N,2) == 1
ind(find(ind==N+1)+1) = N+1
end
ind = convn(ind>N,conv_vec,'same')>0
X = A;
X(ind) = 0
end
来源:https://stackoverflow.com/questions/52537450/elimination-of-consecutive-regions