Search code examples
arraysmatlabif-statementfor-loopclipping

MATLAB: signal clipping method skips array indexes?


The problem: I have roughly isolated data points of the baselines either side of a square pulse signal. I now want to clip these arrays of data points from the 'pulse end' to their respective means (because I still have some data points from the rise and fall of the signal).

the result of my current method seems to skip array indexes

As you can see my method appears to work when starting at the end of an array and clipping backwards, but seems to skip data points when assessing array indexes starting from the beginning of the array.

The code:

baseline1=[1,2,1,2,1,2,1,2,1,2,1,2,1,2,1,2,3,4;1:18];
baseline2=[4,3,2,1,2,1,2,1,2,1,2,1,2,1,2,1,2,1;32:49];
%---------------------------------------------------
figure()
hold on
plot(baseline1(2,:),baseline1(1,:),'k')
plot(baseline2(2,:),baseline2(1,:),'k')
%---------------------------------------------------
%Clip baseline1
arrayMean = mean(baseline1(1,:));
x=size(baseline1,2);
meanCrossed = 0;
arrayClipped = baseline1;
for i=x:-1:1 
    if baseline1(1,i)>arrayMean && meanCrossed == 0
        arrayClipped(:,i)=[];
    else
        meanCrossed = 1;
    end
end
baseline1=arrayClipped;
%---------------------------------------------------
%Clip baseline2
arrayMean = mean(baseline2(1,:));
x=size(baseline2,2);
meanCrossed = 0;
arrayClipped = baseline2;
for i=1:x
    if baseline2(1,i)>arrayMean && meanCrossed == 0
        arrayClipped(:,i)=[];
    else
        meanCrossed = 1;
    end
end
baseline2=arrayClipped;
%---------------------------------------------------
plot(baseline1(2,:),baseline1(1,:),'g','LineWidth',2)
plot(baseline2(2,:),baseline2(1,:),'g','LineWidth',2)

Can anyone advise?


Solution

  • Say you want to delete indices 4 then 2 from a vector of size 4. 4 goes away, so now it's size 3. 2 goes away, making it size 2:

    1 2 3 4
    1 2 3
    1 3
    

    Now say you want to delete indices 2 then 4. 2 goes away, so now it's size 3. Now we delete index 4.... WAIT A SECOND!

    1 2 3 4
    1 3 4
    

    Index 4 doesn't exist, because we shortened the array. The element formerly known as the 4th element is now at index 3.

    By deleting elements, you're changing the indexing of all elements from that point forward. Solution: save all the indices as you compute, and delete them all afterwards:

    for ...
      clipped_indices(end+1) = i;
    end
    
    arrayClipped(:, clipped_indices) = [];
    

    Or, for a cleaner and faster implementation, don't make arrayClipped at all. Instead, make an logical array of all ones of the correct size, and zero them as you find the elements to clip, then index baseline2 with the resulting logical array at the end.