Subset of an array with a moving window

1 visualización (últimos 30 días)
Alex Nickerson
Alex Nickerson el 16 de Abr. de 2021
Editada: Alex Nickerson el 16 de Abr. de 2021
I have the following code for computing structure functions. I have provided examples of "ULs" and "UTs" merely for simplicity.
ULs = rand(1,145); % called in from function
UTs = rand(1,145); % called in from function
nrmax = 145; % called in from function, I just happen to be using 145
for nr = 1:nrmax
Nts = numel(ULs); % number of elements
Umat_L = nan(Nts-nr,nr+1); % must be NaN, so zeros() won't work
Umat_T = nan(Nts-nr,nr+1); % must be NaN, so zeros() won't work
for i = 1:(Nts-nr) % this is
Umat_L(i,:)=ULs(i:i+nr); % the for loop
Umat_T(i,:)=UTs(i:i+nr); % I want to remove
end
end
The nested loop thus takes subsets ULs(1:1+nr), then ULs(2:2+nr), ULs(17:17+nr), etc. Is it possible to replicate this subsetting process without using a loop?
It would improve my code run time if I could remove the nested "for i = 1:(Nts-nr)". However, as I see it, there is no way around this because of the nature of the moving window. I tried the following substitution, but it didn't work.
i = (1:Nts-nr);
inr = i + nr;
Umat_L(i,:) = ULs(i:inr);
Umat_T(i,:) = UTs(i:inr);
  2 comentarios
Rik
Rik el 16 de Abr. de 2021
Many moving window operations can be replaced by movmean and other mov* functions, or by convolutions. The image processing toolbox also contains several useful functions.
Is this code representative of the result you actually want, or is there a further step in calculation?
Alex Nickerson
Alex Nickerson el 16 de Abr. de 2021
Well, as can be seen in the code, there is no moving mean. I don't have access to the Image Processing Toolbox. I just need to be able to get these variable subsets of the code. I will add some details to the original question to further clarify.

Iniciar sesión para comentar.

Respuesta aceptada

Rik
Rik el 16 de Abr. de 2021
The code below relies on implicit expansion to create an index array, which replicates the results from the inner for-loop. Since your code overwrites the results every iteration, you can also have a substantial speed increase by only doing the last one.
nrmax = 145; % called in from function, I just happen to be using 145
ULs = rand(1,nrmax); % called in from function
UTs = rand(1,nrmax); % called in from function
%tic,toc is only an approximate, use timeit for real performance testing
tic,[Umat_L1,Umat_T1]=fun_original(nrmax,ULs,UTs);toc
Elapsed time is 1.689398 seconds.
tic,[Umat_L2,Umat_T2]=fun_unlooped(nrmax,ULs,UTs);toc
Elapsed time is 0.994556 seconds.
if ~isequal(Umat_L1,Umat_L2) || ~isequal(Umat_T1,Umat_T2)
error('results don''t match')
else
disp('everything OK')
end
everything OK
function [Umat_L,Umat_T]=fun_original(nrmax,ULs,UTs)
for slowdown=1:100
for nr = 1:nrmax
Nts = numel(ULs); % number of elements
Umat_L = nan(Nts-nr,nr+1); % must be NaN, so zeros() won't work
Umat_T = nan(Nts-nr,nr+1); % must be NaN, so zeros() won't work
for i = 1:(Nts-nr) % this is
Umat_L(i,:)=ULs(i:i+nr); % the for loop
Umat_T(i,:)=UTs(i:i+nr); % I want to remove
end
end
end
end
function [Umat_L,Umat_T]=fun_unlooped(nrmax,ULs,UTs)
for slowdown=1:100
for nr = 1:nrmax
Nts = numel(ULs); % number of elements
ind=( 0:nr ) + ( 1:(Nts-nr) ).';
Umat_L=ULs(ind);
Umat_T=UTs(ind);
end
end
end
  1 comentario
Alex Nickerson
Alex Nickerson el 16 de Abr. de 2021
Editada: Alex Nickerson el 16 de Abr. de 2021
I have more lines of code that go far beyond the nested loop... I just didn't include them here to save space. This code did exactly what I needed, @Rik, and it cut my code run time (the sample on which I tested it) in half. Thank you for your help.

Iniciar sesión para comentar.

Más respuestas (0)

Categorías

Más información sobre Structures en Help Center y File Exchange.

Community Treasure Hunt

Find the treasures in MATLAB Central and discover how the community can help you!

Start Hunting!

Translated by